问题
My Problem
I have the following spec:
Write a function that given a list of non negative integers, arranges them such that they form the largest possible number. For example, given [50, 2, 1, 9], the largest formed number is 95021.
My Results
I have taken a stab at a solution to the problem, but it fails. For example, given the input [90,91,89,999] the result of this code is [909199989], but it should have been [999919089].
A Description of My Algorithm
In simple words it is a reverse of radix sort.
Steps
1) Based on the values create buckets.
2) Each bucket has list of elements.
3) Sort the list in each bucket.
4) Display the result in the reverse order.
My code
import java.util.ArrayList;
import java.util.Collections;
import java.util.HashMap;
import java.util.List;
import java.util.ListIterator;
import java.util.Map;
import java.util.Scanner;
public class ReverseMaxPossibleNumber {
public static void main(String[] args) {
int[] a = { 50, 2, 1, 9 };
int len = a.length;
String ch = "";
List<Map<String, ArrayList<String>>> list_map = new ArrayList<Map<String, ArrayList<String>>>();
Map<String, ArrayList<String>> map = new HashMap<String, ArrayList<String>>();
for (int i = 0; i < len; i++) {
ch = "" + a[i];
String str = "";
ArrayList<String> arraylist = new ArrayList<String>();
for (int j = 0; j < len; j++) {
str = "" + a[j];
if (ch.charAt(0) == str.charAt(0)) {
arraylist.add(str);
Collections.sort(arraylist);
map.put("" + ch.charAt(0), arraylist);
}
}
}
list_map.add(map);
String str = "";
for (String key : map.keySet()) {
str = map.get(key) + str;
}
str = str.replaceAll("\\D+", "");
System.out.println(str);
}
}
回答1:
Basically, the numbers need to be ordered in a certain way to form the maximum possible number. Consider this logic:
- Take any 2 numbers
aandb - If
abis bigger thanbathenashould come beforeb. Right?- Where
abisaandbconcatenated, so ifa = 4andb = 43thenabis443andbais434
- Where
You could implement this in a custom comparator, and pass it to Collections.sort, like this:
public String maxNumber(int[] numbers) {
// convert int[] -> List<String>
List<String> list = new ArrayList<>(numbers.length);
for (int num : numbers) {
list.add(String.valueOf(num));
}
// sort using custom comparator
Collections.sort(list, (o1, o2) -> (o2 + o1).compareTo(o1 + o2));
// join sorted items, forming max possible number
return String.join("", list);
}
Here is basically the same code using Java 8: (thanks @marcospereira!)
public String maxNumber(Integer ... numbers) {
return Stream.of(numbers)
.filter(n -> n >= 0)
.map(Object::toString)
.sorted((s1, s2) -> (s2 + s1).compareTo(s1 + s2))
.collect(Collectors.joining());
}
回答2:
No matter how you combine the numbers they produce a number with the same number of digits. This means you want to sort them to put the biggest digits first. In fact this is to opposite problem of sorting numbers inside a string because you want to sort the numbers like you would Strings (from the first digit first)
int[] a = {90, 91, 89, 999};
long num = Long.parseLong(
IntStream.of(a)
.mapToObj(Integer::toString)
// reverse sort them as Strings.
.sorted((x, y) -> (y + x).compareTo(x + y))
.collect(Collectors.joining()));
System.out.println(num);
prints
999919089
来源:https://stackoverflow.com/questions/35757625/write-a-function-that-given-a-list-of-non-negative-integers-arranges-them-such