We are given two arrays, we need to find the longest possible bitonic sequence such that increasing part must be from first array and should be a subsequence of first array. Similarly, decreasing part of must be from second array and should be a subsequence of it.

Examples:

Input : arr1[] = {1, 5, 2, 4, 3, 5}, arr2[] = {8, 6, 4, 7, 3, 2} Output : 1, 2, 4, 5, 8, 6, 4, 3, 2 Input : arr1[] = {2, 0, 1, 3, 4}, arr2[] = {5, 3, 2, 1} Output : 0, 1, 2, 3, 4, 5, 3, 2, 1

The idea is to use largest increasing sequence from array1 and largest decreasing sequence from array2 and then combine both to get our result.

## C++

`// CPP to find largest bitonic sequence such that ` `#include <bits/stdc++.h> ` `using` `namespace` `std; ` ` ` `vector<` `int` `> res; ` ` ` `// utility Binary search ` `int` `GetCeilIndex(` `int` `arr[], vector<` `int` `>& T, ` `int` `l, ` ` ` `int` `r, ` `int` `key) ` `{ ` ` ` `while` `(r - l > 1) { ` ` ` `int` `m = l + (r - l) / 2; ` ` ` `if` `(arr[T[m]] >= key) ` ` ` `r = m; ` ` ` `else` ` ` `l = m; ` ` ` `} ` ` ` `return` `r; ` `} ` ` ` `// function to find LIS in reverse form ` `void` `LIS(` `int` `arr[], ` `int` `n) ` `{ ` ` ` `// Add boundary case, when array n is zero ` ` ` `// Depend on smart pointers ` ` ` `vector<` `int` `> tailIndices(n, 0); ` `// Initialized with 0 ` ` ` `vector<` `int` `> prevIndices(n, -1); ` `// initialized with -1 ` ` ` ` ` `int` `len = 1; ` `// it will always point to empty location ` ` ` `for` `(` `int` `i = 1; i < n; i++) { ` ` ` ` ` `// new smallest value ` ` ` `if` `(arr[i] < arr[tailIndices[0]]) ` ` ` `tailIndices[0] = i; ` ` ` ` ` `// arr[i] wants to extend largest subsequence ` ` ` `else` `if` `(arr[i] > arr[tailIndices[len - 1]]) { ` ` ` `prevIndices[i] = tailIndices[len - 1]; ` ` ` `tailIndices[len++] = i; ` ` ` `} ` ` ` ` ` `// arr[i] wants to be a potential candidate of ` ` ` `// future subsequence ` ` ` `// It will replace ceil value in tailIndices ` ` ` `else` `{ ` ` ` `int` `pos = GetCeilIndex(arr, tailIndices, -1, ` ` ` `len - 1, arr[i]); ` ` ` `prevIndices[i] = tailIndices[pos - 1]; ` ` ` `tailIndices[pos] = i; ` ` ` `} ` ` ` `} ` ` ` ` ` `// put LIS into vector ` ` ` `for` `(` `int` `i = tailIndices[len - 1]; i >= 0; i = prevIndices[i]) ` ` ` `res.push_back(arr[i]); ` `} ` ` ` `// function for finding longest bitonic seq ` `void` `longestBitonic(` `int` `arr1[], ` `int` `n1, ` `int` `arr2[], ` `int` `n2) ` `{ ` ` ` `// find LIS of array 1 in reverse form ` ` ` `LIS(arr1, n1); ` ` ` ` ` `// reverse res to get LIS of first array ` ` ` `reverse(res.begin(), res.end()); ` ` ` ` ` `// reverse array2 and find its LIS ` ` ` `reverse(arr2, arr2 + n2); ` ` ` `LIS(arr2, n2); ` ` ` ` ` `// print result ` ` ` `for` `(` `int` `i = 0; i < res.size(); i++) ` ` ` `cout << res[i] << ` `" "` `; ` `} ` ` ` `// driver preogram ` `int` `main() ` `{ ` ` ` `int` `arr1[] = { 1, 2, 4, 3, 2 }; ` ` ` `int` `arr2[] = { 8, 6, 4, 7, 8, 9 }; ` ` ` `int` `n1 = ` `sizeof` `(arr1) / ` `sizeof` `(arr1[0]); ` ` ` `int` `n2 = ` `sizeof` `(arr2) / ` `sizeof` `(arr2[0]); ` ` ` `longestBitonic(arr1, n1, arr2, n2); ` ` ` `return` `0; ` `} ` |

*chevron_right*

*filter_none*

## Java

`// Java to find largest bitonic sequence such that ` `import` `java.util.*; ` ` ` `class` `GFG ` `{ ` ` ` `static` `Vector<Integer> res = ` `new` `Vector<>(); ` ` ` ` ` `// utility Binary search ` ` ` `static` `Integer GetCeilIndex(Integer[] arr, Integer[] T, ` ` ` `Integer l, Integer r, Integer key) ` ` ` `{ ` ` ` `while` `(r - l > ` `1` `) ` ` ` `{ ` ` ` `Integer m = l + (r - l) / ` `2` `; ` ` ` `if` `(arr[T[m]] >= key) ` ` ` `r = m; ` ` ` `else` ` ` `l = m; ` ` ` `} ` ` ` `return` `r; ` ` ` `} ` ` ` ` ` `// function to find LIS in reverse form ` ` ` `static` `void` `LIS(Integer[] arr, Integer n) ` ` ` `{ ` ` ` ` ` `// Add boundary case, when array n is zero ` ` ` `// Depend on smart pointers ` ` ` `Integer[] tailIndices = ` `new` `Integer[n]; ` ` ` `Integer[] prevIndices = ` `new` `Integer[n]; ` ` ` `Arrays.fill(tailIndices, ` `0` `); ` `// Initialized with 0 ` ` ` `Arrays.fill(prevIndices, -` `1` `); ` `// initialized with -1 ` ` ` ` ` `Integer len = ` `1` `; ` `// it will always point to empty location ` ` ` `for` `(Integer i = ` `1` `; i < n; i++) ` ` ` `{ ` ` ` `// new smallest value ` ` ` `if` `(arr[i] < arr[tailIndices[` `0` `]]) ` ` ` `tailIndices[` `0` `] = i; ` ` ` ` ` `// arr[i] wants to extend largest subsequence ` ` ` `else` `if` `(arr[i] > arr[tailIndices[len - ` `1` `]]) ` ` ` `{ ` ` ` `prevIndices[i] = tailIndices[len - ` `1` `]; ` ` ` `tailIndices[len++] = i; ` ` ` `} ` ` ` ` ` `// arr[i] wants to be a potential candidate of ` ` ` `// future subsequence ` ` ` `// It will replace ceil value in tailIndices ` ` ` `else` ` ` `{ ` ` ` `Integer pos = GetCeilIndex(arr, ` ` ` `tailIndices, -` `1` `, len - ` `1` `, arr[i]); ` ` ` `prevIndices[i] = tailIndices[pos - ` `1` `]; ` ` ` `tailIndices[pos] = i; ` ` ` `} ` ` ` `} ` ` ` ` ` `// put LIS into vector ` ` ` `for` `(Integer i = tailIndices[len - ` `1` `]; i >= ` `0` `; i = prevIndices[i]) ` ` ` `res.add(arr[i]); ` ` ` `} ` ` ` ` ` `// function for finding longest bitonic seq ` ` ` `static` `void` `longestBitonic(Integer[] arr1, Integer n1, ` ` ` `Integer[] arr2, Integer n2) ` ` ` `{ ` ` ` `// find LIS of array 1 in reverse form ` ` ` `LIS(arr1, n1); ` ` ` ` ` `// reverse res to get LIS of first array ` ` ` `Collections.reverse(res); ` ` ` ` ` `// reverse array2 and find its LIS ` ` ` `Collections.reverse(Arrays.asList(arr2)); ` ` ` `LIS(arr2, n2); ` ` ` ` ` `// print result ` ` ` `for` `(Integer i = ` `0` `; i < res.size(); i++) ` ` ` `System.out.print(res.elementAt(i) + ` `" "` `); ` ` ` `} ` ` ` ` ` `// Driver Code ` ` ` `public` `static` `void` `main(String[] args) ` ` ` `{ ` ` ` `Integer[] arr1 = { ` `1` `, ` `2` `, ` `4` `, ` `3` `, ` `2` `}; ` ` ` `Integer[] arr2 = { ` `8` `, ` `6` `, ` `4` `, ` `7` `, ` `8` `, ` `9` `}; ` ` ` `Integer n1 = arr1.length; ` ` ` `Integer n2 = arr2.length; ` ` ` `longestBitonic(arr1, n1, arr2, n2); ` ` ` `} ` `} ` ` ` `// This code is contributed by ` `// sanjeev2552 ` |

*chevron_right*

*filter_none*

## Python3

`# Python3 to find largest bitonic sequence such that ` `res ` `=` `[] ` ` ` `# utility Binary search ` `def` `GetCeilIndex(arr,T, l,r, key): ` ` ` `while` `(r ` `-` `l > ` `1` `): ` ` ` `m ` `=` `l ` `+` `(r ` `-` `l) ` `/` `/` `2` `; ` ` ` `if` `(arr[T[m]] >` `=` `key): ` ` ` `r ` `=` `m ` ` ` `else` `: ` ` ` `l ` `=` `m ` ` ` `return` `r ` ` ` `# function to find LIS in reverse form ` `def` `LIS(arr, n): ` ` ` ` ` `# Add boundary case, when array n is zero ` ` ` `# Depend on smart pointers ` ` ` `tailIndices ` `=` `[` `0` `]` `*` `(n) ` `#Initialized with 0 ` ` ` `prevIndices ` `=` `[` `-` `1` `]` `*` `(n) ` `#initialized with -1 ` ` ` ` ` `leN` `=` `1` `# it will always poto empty location ` ` ` `for` `i ` `in` `range` `(` `1` `, n): ` ` ` ` ` `# new smallest value ` ` ` `if` `(arr[i] < arr[tailIndices[` `0` `]]): ` ` ` `tailIndices[` `0` `] ` `=` `i ` ` ` ` ` `# arr[i] wants to extend largest subsequence ` ` ` `elif` `(arr[i] > arr[tailIndices[` `leN` `-` `1` `]]): ` ` ` `prevIndices[i] ` `=` `tailIndices[` `leN` `-` `1` `] ` ` ` `tailIndices[` `leN` `] ` `=` `i ` ` ` `leN` `+` `=` `1` ` ` ` ` `# arr[i] wants to be a potential candidate of ` ` ` `# future subsequence ` ` ` `# It will replace ceil value in tailIndices ` ` ` `else` `: ` ` ` `pos ` `=` `GetCeilIndex(arr, tailIndices, ` `-` `1` `, ` ` ` `leN` `-` `1` `, arr[i]) ` ` ` `prevIndices[i] ` `=` `tailIndices[pos ` `-` `1` `] ` ` ` `tailIndices[pos] ` `=` `i ` ` ` ` ` `# put LIS into vector ` ` ` `i ` `=` `tailIndices[` `leN` `-` `1` `] ` ` ` `while` `(i >` `=` `0` `): ` ` ` ` ` `# print(i) ` ` ` `res.append(arr[i]) ` ` ` `i ` `=` `prevIndices[i] ` ` ` `# function for finding longest bitonic seq ` `def` `longestBitonic(arr1, n1, arr2, n2): ` ` ` `global` `res ` ` ` ` ` `# find LIS of array 1 in reverse form ` ` ` `LIS(arr1, n1) ` ` ` ` ` `# reverse res to get LIS of first array ` ` ` `res ` `=` `res[::` `-` `1` `] ` ` ` ` ` `# reverse array2 and find its LIS ` ` ` `arr2 ` `=` `arr2[::` `-` `1` `] ` ` ` `LIS(arr2, n2) ` ` ` ` ` `# print result ` ` ` `for` `i ` `in` `res: ` ` ` `print` `(i,end` `=` `" "` `) ` ` ` `# Driver program ` ` ` `arr1 ` `=` `[` `1` `, ` `2` `, ` `4` `, ` `3` `, ` `2` `] ` `arr2 ` `=` `[` `8` `, ` `6` `, ` `4` `, ` `7` `, ` `8` `, ` `9` `] ` `n1 ` `=` `len` `(arr1) ` `n2 ` `=` `len` `(arr2) ` `longestBitonic(arr1, n1, arr2, n2); ` ` ` `# This code is contributed by mohit kumar 29 ` |

*chevron_right*

*filter_none*

**Output:**

1 2 3 8 6 4

**Time Complexity :** O(n Log n)

Please note that O(n Log n) implementation of LIS is used

This article is contributed by **Shivam Pradhan (anuj_charm)**. If you like GeeksforGeeks and would like to contribute, you can also write an article using contribute.geeksforgeeks.org or mail your article to contribute@geeksforgeeks.org. See your article appearing on the GeeksforGeeks main page and help other Geeks.

Please write comments if you find anything incorrect, or you want to share more information about the topic discussed above.

Attention reader! Don’t stop learning now. Get hold of all the important DSA concepts with the **DSA Self Paced Course** at a student-friendly price and become industry ready.

## Recommended Posts:

- Longest Reverse Bitonic Sequence
- Construction of Longest Increasing Subsequence(LIS) and printing LIS sequence
- Length of the longest increasing subsequence such that no two adjacent elements are coprime
- Longest increasing sub-sequence formed by concatenating array to itself N times
- Longest increasing sequence by the boundary elements of an Array
- Length of the longest subsequence such that xor of adjacent elements is non-decreasing
- Longest Increasing Subsequence using Longest Common Subsequence Algorithm
- Number of ways to divide string in sub-strings such to make them in lexicographically increasing sequence
- Minimum number of elements which are not part of Increasing or decreasing subsequence in array
- Pyramid form (increasing then decreasing) consecutive array using reduce operations
- Longest Bitonic Subsequence | DP-15
- Printing Longest Bitonic Subsequence
- Longest Bitonic Subsequence in O(n log n)
- Print Longest Bitonic subsequence (Space Optimized Approach)
- Maximum contiguous decreasing sequence obtained by removing any one element
- Find the Longest Increasing Subsequence in Circular manner
- Longest Decreasing Subsequence
- Possible cuts of a number such that maximum parts are divisible by 3
- Count ways to partition a string such that both parts have equal distinct characters
- Split the string into minimum parts such that each part is in the another string