Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Array : Largest possible number

Given an array of elements find the largest possible number that can be formed by using the elements of the array.
eg: 10 9
ans: 910
2 3 5 78
ans: 78532
100 9
ans: 9100

I know this problem has a solution using customized string comparator but i dont understand how it really works.

    #include <iostream>
    #include <string>
    #include <algorithm>
    #include <vector>

    using namespace std;


    bool compare ( string a, string b )  
    {  
            return atoi( (a+b).c_str() ) < atoi((b+a).c_str() );  
    }

    int main()  
    {  
            vector<string> vs;  
            string s;  
            while ( cin >> s ) {  
                    vs.push_back(s);  
            }  
            sort( vs.begin(), vs.end(), compare );  
            for ( int i = vs.size()-1; i >= 0; i-- ) {  
                    cout << vs[i];  
            }  
    }   

Can anyone propose an algorithm to solve this problem? Explanation of the above comparator will be appreciated. Thank you

like image 209
Pritpal Avatar asked Jun 25 '11 06:06

Pritpal


People also ask

How do you find the largest number in an array?

Initialize max with the first element initially, to start the comparison. Then traverse the given array from second element till end, and for each element: Compare the current element with max. If the current element is greater than max, then replace the value of max with the current element.

What is the largest possible number?

The biggest number referred to regularly is a googolplex (10googol), which works out as 1010^100.

What is the biggest number besides infinity?

There is no biggest, last number … except infinity. Except infinity isn't a number.

How do you find the greatest possible number?

There is no such thing as a highest possible number. No matter what number you have, there is always a larger one. (For example, you could always add 1 to your number to get a larger number).


4 Answers

Indeed, if we have two strings S and T, we will most commonly concatenate them in lexicographically reverse order, to make the biggest digits come forward. However, this approach doesn't perfectly work, when one of these strings is a prefix for the other one.
Let T = SA, i.e. S is a prefix of T. We have two choices of concatenation: SSA and SAS. Obviously our choice will depend on which number is bigger: AS or SA. Below is the modification of your code which satisfies this algo:

#include <iostream>
#include <string>
#include <algorithm>
#include <vector>

using namespace std;


bool compare ( string a, string b )  
{  
        int i, j;
        for( i = 0; i < a.size() && i < b.size(); ++i )
               if( a[ i ] != b[ i ] )
                     break;
        if( i < a.size() && i < b.size() ) //  if digit mismatch happened
               return a[ i ] < b[ i ];
        if( i == a.size() )                // a is a prefix for b
        {
               string suffix = b.substr( i );
               return a + suffix < suffix + a;
        }
        else                               // b is a prefix for a
        {
               string suffix = a.substr( i );
               return suffix + b < b + suffix;
        }
}

int main()  
{  
        vector<string> vs;  
        string s;  
        while ( cin >> s ) {  
                vs.push_back(s);  
        }  
        sort( vs.begin(), vs.end(), compare );  
        for ( int i = vs.size()-1; i >= 0; i-- ) {  
                cout << vs[i];  
        }  
}
like image 164
Grigor Gevorgyan Avatar answered Sep 19 '22 02:09

Grigor Gevorgyan


The comparator compares two strings if the combination a+b comes before or after b+a. Thus e.g. it says that for input a=4; b=3 the string "34" is smaller than "43" and thus 4 should be before 3.

The numbers 2 3 5 78 will therefore be sorted into 78 5 3 2 and thus the result is 78532.

like image 41
Howard Avatar answered Sep 22 '22 02:09

Howard


Just sort them into lexicographic order by comparing the digits from left to right. This way the larger digits appear first, thereby making the concatenated number larger.

EDIT: As Grigor points out, you must first reverse the strings, the sort them into reverse lex order, then concatenate and reverse the result.

like image 32
PengOne Avatar answered Sep 23 '22 02:09

PengOne


You are using comparator operator to find the bigger of two possible numbers formed by concatenating two numbers(strings) in both possible ways a+b and b+a. Since you are interested in comparing magnitude of numbers, atoi() function is used to convert string to corresponding numbers.
But this conversion is not required. As the length of two strings a+b and b+a is same, lexicographical comparison is as good as magnitude of numbers. Conversion is only required when length of two stings compared is not equal.

like image 31
Terminal Avatar answered Sep 22 '22 02:09

Terminal