Given a number num containing n digits. The problem is to find the next greater number using the same set of digits in num on the basis of the given precedence of digits. For example the precedence of digits is given as 1, 6, 4, 5, 2, 9, 8, 0, 7, 3 which simply means 1 < 6 < 4 < 5 < 2 < 9 < 8 < 0 < 7 < 3. If next greater number cannot be formed then print the original number.
Examples:
Input : num = "231447" pre[] = {1, 6, 7, 5, 2, 9, 8, 0, 4, 3} Output : 237144 According to the precedence of digits 1 is being considered as the smallest digit and 3 is being considered as the largest digit. Input : num = "471" pre[] = {1, 6, 7, 5, 2, 9, 8, 0, 4, 3} Output : 471
Approach: Following are the steps:
- Create a priority[] array of size ’10’. With the help of precedence array pre[] assign a priority number to each digit in priority[] where ‘1’ is being considered as smallest priority and ’10’ as the highest priority.
- Using the STL C++ next_permutation with a manually defined compare function find the next greater permutation.
C++
// C++ implementation to find the next greater number // on the basis of precedence of digits #include <bits/stdc++.h> using namespace std; #define DIGITS 10 // priority[] to store the priority of digits // on the basis of pre[] array. Here '1' is being // considered as the smallest priority as '10' as // the highest priority int priority[DIGITS]; // comparator function used for finding the // the next greater permutation struct compare { bool operator()( char x, char y) { return priority[x - '0' ] < priority[y - '0' ]; } }; // function to find the next greater number // on the basis of precedence of digits void nextGreater( char num[], int n, int pre[]) { memset (priority, 0, sizeof (priority)); // variable to assign priorities to digits int assign = 1; // assigning priorities to digits on // the basis of pre[] for ( int i = 0; i < DIGITS; i++) { priority[pre[i]] = assign; assign++; } // find the next greater permutation of 'num' // using the compare() function bool a = next_permutation(num, num + n, compare()); // if the next greater permutation does not exists // then store the original number back to 'num' // using 'pre_permutation'. if (a == false ) prev_permutation(num, num + n, compare()); } // Driver program to test above int main() { char num[] = "231447" ; int n = strlen (num); int pre[] = {1, 6, 7, 5, 2, 9, 8, 0, 4, 3}; nextGreater(num, n, pre); cout << "Next Greater: " << num; return 0; } |
Java
// GFG // JAVA implementation to find the next greater number // on the basis of precedence of digits import java.util.Arrays; public class Main { static final int DIGITS = 10 ; // priority[] to store the priority of digits // on the basis of pre[] array. Here '1' is being // considered as the smallest priority as '10' as // the highest priority static int [] priority = new int [DIGITS]; // comparator function used for finding the // the next greater permutation static class Compare { boolean compare( char x, char y) { return priority[x - '0' ] < priority[y - '0' ]; } } // function to find the next greater number // on the basis of precedence of digits static void nextGreater( char [] num, int n, int [] pre) { Arrays.fill(priority, 0 ); // variable to assign priorities to digits int assign = 1 ; // assigning priorities to digits on // the basis of pre[] for ( int i = 0 ; i < DIGITS; i++) { priority[pre[i]] = assign; assign++; } // find the next greater permutation of 'num' // using the compare() function boolean a = nextPermutation(num, n, new Compare()); // if the next greater permutation does not exists // then store the original number back to 'num' // using 'pre_permutation'. if (!a) prevPermutation(num, n, new Compare()); } static boolean nextPermutation( char [] a, int n, Compare c) { int i = n - 2 ; while (i >= 0 && c.compare(a[i], a[i + 1 ])) { i--; } if (i < 0 ) return false ; int j = n - 1 ; while (c.compare(a[i], a[j])) { j--; } swap(a, i, j); reverse(a, i + 1 , n - 1 ); return true ; } static void prevPermutation( char [] a, int n, Compare c) { int i = n - 2 ; while (i >= 0 && !c.compare(a[i], a[i + 1 ])) { i--; } if (i < 0 ) return ; int j = n - 1 ; while (!c.compare(a[i], a[j])) { j--; } swap(a, i, j); reverse(a, i + 1 , n - 1 ); } static void swap( char [] a, int i, int j) { char tmp = a[i]; a[i] = a[j]; a[j] = tmp; } static void reverse( char [] a, int l, int r) { while (l < r) { swap(a, l, r); l++; r--; } } // Driver program to test above public static void main(String[] args) { char [] num = "237144" .toCharArray(); int n = num.length; int [] pre = { 1 , 6 , 7 , 5 , 2 , 9 , 8 , 0 , 4 , 3 }; nextGreater(num, n, pre); System.out.println( "Next Greater: " + new String(num)); } } // |
Python3
# Python Code import itertools # priority[] to store the priority of digits # on the basis of pre[] array. Here '1' is being # considered as the smallest priority as '10' as # the highest priority priority = [ 0 ] * 10 # function to find the next greater number # on the basis of precedence of digits def nextGreater(num, n, pre): assign = 1 # assigning priorities to digits on # the basis of pre[] for i in range ( 10 ): priority[pre[i]] = assign assign + = 1 # find the next greater permutation of 'num' # using the lexicographical_compare() function a = lexicographical_compare(num, n) # if the next greater permutation does not exists # then store the original number back to 'num' # using 'pre_permutation'. if (a = = False ): pre_permutation(num, n) # function to find the next greater permutation # using the compare() function def lexicographical_compare(a, n): i = n - 2 while (i > = 0 and a[i] > = a[i + 1 ]): i - = 1 if (i < 0 ): return False j = n - 1 while (a[j] < = a[i]): j - = 1 a[i], a[j] = a[j], a[i] a[i + 1 :] = reversed (a[i + 1 :]) return True # function to find the previous permutation # using the compare() function def pre_permutation(a, n): i = n - 2 while (i > = 0 and a[i] < = a[i + 1 ]): i - = 1 if (i < 0 ): return j = n - 1 while (a[j] > = a[i]): j - = 1 a[i], a[j] = a[j], a[i] a[i + 1 :] = reversed (a[i + 1 :]) # Driver program to test above if __name__ = = "__main__" : num = "237144" n = len (num) pre = [ 1 , 6 , 7 , 5 , 2 , 9 , 8 , 0 , 4 , 3 ] nextGreater( list (num), n, pre) print ( "Next Greater:" , "".join(num)) |
C#
// C# implementation to find the next greater number // on the basis of precedence of digits using System; using System.Linq; using System.Collections.Generic; class Gfg { // priority[] to store the priority of digits // on the basis of pre[] array. Here '1' is being // considered as the smallest priority as '10' as // the highest priority static int [] priority = new int [10]; // Comparator function used for finding the next greater permutation class DigitComparer : IComparer< char > { public int Compare( char x, char y) { return priority[x - '0' ].CompareTo(priority[y - '0' ]); } } // Function to find the next greater number on the basis of precedence of digits static void NextGreater( char [] num, int n, int [] pre) { // Assigning priorities to digits on the basis of pre[] int assign = 1; foreach ( int i in pre) { priority[i] = assign; assign++; } // Find the next greater permutation of 'num' using the DigitComparer function bool a = ArrayExtensions.NextPermutation(num, new DigitComparer()); // If the next greater permutation does not exist, then store the original number back to 'num' // using 'PreviousPermutation'. if (!a) { ArrayExtensions.PreviousPermutation(num, new DigitComparer()); } } // Driver program to test above static void Main( string [] args) { char [] num = "231447" .ToCharArray(); int n = num.Length; int [] pre = new int [] { 1, 6, 7, 5, 2, 9, 8, 0, 4, 3 }; NextGreater(num, n, pre); Console.WriteLine( "Next Greater: " + new string (num)); } } // Extension methods for array to implement NextPermutation and PreviousPermutation public static class ArrayExtensions { // Implementation of NextPermutation public static bool NextPermutation<T>( this T[] array, IComparer<T> comparer) { for ( int i = array.Length - 2; i >= 0; i--) { if (comparer.Compare(array[i], array[i + 1]) < 0) { int j = array.Length - 1; while (comparer.Compare(array[i], array[j]) >= 0) { j--; } T temp = array[i]; array[i] = array[j]; array[j] = temp; Array.Reverse(array, i + 1, array.Length - i - 1); return true ; } } return false ; } // Implementation of PreviousPermutation public static bool PreviousPermutation<T>( this T[] array, IComparer<T> comparer) { for ( int i = array.Length - 2; i >= 0; i--) { if (comparer.Compare(array[i], array[i + 1]) > 0) { int j = array.Length - 1; while (comparer.Compare(array[i], array[j]) <= 0) { j--; } T temp = array[i]; array[i] = array[j]; array[j] = temp; Array.Reverse(array, i + 1, array.Length - i - 1); return true ; } } return false ; } } |
Javascript
// Javascript implementation to find the next greater number // on the basis of precedence of digits // priority[] to store the priority of digits // on the basis of pre[] array. Here '1' is being // considered as the smallest priority as '10' as // the highest priority const DIGITS = 10; const priority = new Array(DIGITS).fill(0); // comparator function used for finding the // the next greater permutation function compare(x, y) { return priority[x.charCodeAt(0) - '0' .charCodeAt(0)] < priority[y.charCodeAt(0) - '0' .charCodeAt(0)]; } // function to find the next greater number // on the basis of precedence of digits function nextGreater(num, n, pre) { priority.fill(0); // variable to assign priorities to digits let assign = 1; // assigning priorities to digits on // the basis of pre[] for (let i = 0; i < DIGITS; i++) { priority[pre[i]] = assign; assign++; } // find the next greater permutation of 'num' // using the compare() function let a = num.split( '' ); a.sort(compare); a = a.join( '' ); // if the next greater permutation does not exists // then store the original number back to 'num' // using 'pre_permutation'. if (a === num.split( '' ).sort().join( '' )) { a = num.split( '' ); //This article is contributed by rutikbhosale. a.sort(compare); a.reverse(); a = a.join( '' ); } num = a; } // Driver program to test above let num = "231447" ; let n = num.length; let pre = [1, 6, 7, 5, 2, 9, 8, 0, 4, 3]; nextGreater(num, n, pre); console.log( "Next Greater: " + num); |
Next Greater: 237144
Time Complexity: O(n).
Auxiliary Space: O(1).
Ready to dive in? Explore our Free Demo Content and join our DSA course, trusted by over 100,000 neveropen!