J'ai une liste d'objets qui contiennent des valeurs stockées sous forme de chaînes mais qui sont en fait des nombres et j'essaie de trouver un moyen d'analyser des chaînes en entiers dans un flux Java pour les trier numériquement. Voici ce que j'ai obtenu jusqu'à présent.
3356001017053000000000000 3356001017002000000000000 3356001017004000000000000 3356001017026000000000000 5101004003020000000000000 4123000006002510000000000 4758000005010000000000000
Pour le moment, ce genre de travail fonctionne, mais le problème est que parce que ces nombres sont en fait des chaînes, il trie les nombres lexicographiquement, pas numériquement. Existe-t-il un moyen d'incorporer l'analyse dans le flux? Tous les nombres sont remplis pour avoir la même taille.
List<SearchResultObject> returnedValues = doTheSearchMethod(); returnedValues = returnedValues .stream() .sorted(Comparator.comparing(SearchResultObject::getNumber)) .collect(Collectors.toList());
4 Réponses :
utilisez compareLong
puis analysez long. les nombres sont trop grands pour les entiers.
returnedValues.sort(Comparator.comparingLong(sro->Long.parseLong(sro.getNumber())));
Pour simplement trier, vous n'avez pas besoin de flux, utilisez simplement un Comparator
personnalisé en utilisant l'expression lambda
Collections.sort(returnedValues,c);
Et puis utilisez Collections.sort code > méthode
Comparator<SearchResultObject> c = Comparator.comparingLong(s->Long.parseLong(s.getNumber()));
Vous n'avez pas besoin d'utiliser l'API Streams pour trier la liste, vous pouvez utiliser directement la méthode sort ()
depuis l'interface de liste. Vous devez juste vous assurer que vous fournissez un comparateur
approprié à la méthode sort ()
.
Comme vous l'avez mentionné, vous pouvez utiliser directement:
Before sorting SearchResultObject{number='100'} SearchResultObject{number='2'} SearchResultObject{number='10'} After sorting SearchResultObject{number='2'} SearchResultObject{number='10'} SearchResultObject{number='100'}
comparateur pour comparer les chaînes.
Cependant, comme vous avez besoin que la liste soit triée en comparant Entier / Long, vous pouvez utiliser ce qui suit:
Pour un entier:
list.sort (Comparator.comparingInt (s -> Integer.parseInt (s.getNumber ())));
Pour longtemps:
list.sort (Comparator.comparingLong (s -> Long.parseLong (s.getNumber ())));
Vous pouvez vérifier la sortie pour le code suivant ci-dessous:
Comparator.comparing(SearchResultObject::getNumber)
La sortie ci-dessus est basée sur l'hypothèse de SearchResultObject
contient un numéro
comme champ.
Si vous pouvez modifier Et l'appel est Si vous ne pouvez pas modifier le SearchResultObject
, ajoutez-y une méthode en convertissant la String
en BigInteger
et utilisez-la dans votre Comparator code>
returnedValues.stream()
.sorted(
Comparator.comparing(
sro -> new BigInteger(sro.getNumber())
)
)
.collect(toList());
returnedValues.stream()
.sorted(
Comparator.comparing(
SearchResultObject::getNumberAsBigInteger
)
)
.collect(Collectors.toList());
SearchResultObject
classe, alors vous devrez personnaliser un peu votre Comparateur
, mais rien de trop compliqué public SearchResultObject {
...
public BigInteger getNumberAsBigInteger() {
return new BigInteger(this.number);
}
...
}
Qu'en est-il du changement de
Search Result Object.get Number ()
pour qu'il renvoie une instancelong
ouNumber
?