3 votes

Manière idiomatique de s'assurer que plusieurs valeurs sont égales

Disons que j'ai une liste de plusieurs variables primitives :

final int a = 3;
final int b = 4;
final int c = 4;
final int d = 4;
final int e = 4;

Quel est le moyen idiomatique de s'assurer qu'ils ont tous la même valeur ? La façon la plus évidente est simplement

if (a == b && a == c && a == d && a == e) // ...

Mais je pense que cela est source d'erreurs et difficile à lire, en particulier lorsque les variables ont des noms propres, contrairement à mon exemple.

if (  numCategories == numTypes && numCategories == numColours
   && numCategories == numStyles && numCategories == numPrices) // ...

Ce serait bien si nous pouvions faire la comparaison de cette manière :

if (a == b == c == d == e)

mais il est évident que a == b se résout en un booléen, nous ne pouvons donc pas le comparer à c .

Existe-t-il une fonction de bibliothèque dans le JDK ou une autre bibliothèque utilitaire avec une signature similaire ?

static boolean areEqual(int... numbers)

nous pourrions alors l'utiliser comme suit :

if (areEqual(a, b, c, d, e)) //...

Je pourrais facilement écrire une telle fonction moi-même, mais pourquoi réinventer la roue si ce n'est pas nécessaire ?

Il y a peut-être une autre façon idiomatique d'accomplir cela qui m'échappe.

3voto

Eran Points 35360

Utilisation Stream vous pouvez profiter de certaines méthodes pratiques pour atteindre votre objectif.

Vous pouvez utiliser Stream ou IntStream 's distinct() combinée avec count() pour trouver le nombre d'éléments uniques :

Para int variables :

if (IntStream.of(a,b,c,d,e).distinct().count() == 1) {

}

Pour les variables de type référence :

if (Stream.of(a,b,c,d,e).distinct().count() == 1) {

}

Un autre moyen, probablement moins efficace (mais je le garde ici puisque c'est la première chose à laquelle j'ai pensé), consiste à créer un fichier Stream de tous les éléments que vous souhaitez comparer, puis les rassembler dans un Set et en vérifiant la taille du Set est égal à 1 (puisque Set n'autorise pas les doublons) :

if (IntStream.of(a,b,c,d,e).boxed().collect(Collectors.toSet()).size() == 1) {

}

ou

if (Stream.of(a,b,c,d,e).collect(Collectors.toSet()).size() == 1) {

}

pour le général Object s.

3voto

Guy Points 16347

Une option naïve consiste à construire des méthodes qui reçoivent toutes les variables en tant que varargs et les comparent l'une après l'autre. Si l'une d'entre elles est différente, vous obtiendrez false

public static boolean areEqual(int...nums)
{
    for (int i = 0 ; i < nums.length - 1 ; ++i) {
        if (nums[i] != nums[i + 1]) {
            return false;
        }
    }
    return true;
}

Utilisations

if (areEqual(a, b, c, d, e))

0voto

Michael Points 20266

J'aime cette approche. Il n'y a pas de boîte automatique ni de chiffres magiques.

Selon la documentation En outre, il s'agit d'un court-circuit, donc potentiellement plus efficace que les autres méthodes. Plus important encore, il est très facile à lire.

IntStream.of(a, b, c, d).allMatch(x -> x == e);

Crédit à <a href="https://stackoverflow.com/users/4910279/saka1029">saka1029 </a>.

Prograide.com

Prograide est une communauté de développeurs qui cherche à élargir la connaissance de la programmation au-delà de l'anglais.
Pour cela nous avons les plus grands doutes résolus en français et vous pouvez aussi poser vos propres questions ou résoudre celles des autres.

Powered by:

X