Convertir booléen en int en Java


350

Quelle est la façon la plus acceptée de convertir un booleanen un inten Java?


8
Selon vous, à quels nombres entiers correspondaient-ils trueet falserespectivement?
Thorbjørn Ravn Andersen

4
Certaines langues ont une conversion implicite d'int en booléen. Java ne le fait pas. Cependant, l'implémentation officielle a des packages SQL, et je pense qu'ils convertissent "false" en 0.
hpique

4
@Peter Lawrey Pas si vous souhaitez interagir avec d'autres systèmes qui n'ont pas de booléen comme type de données non numérique.
hpique

6
@Peter Lawrey La question ne concerne pas vraiment la cartographie des valeurs. Il s'agit de savoir comment effectuer la conversion de la manière la plus claire et la plus acceptée.
hpique

7
Techniquement, le compilateur Java définit déjà un mappage. True et False sont compilés respectivement à 1 et 0.
Antimony

Réponses:


583
int myInt = myBoolean ? 1 : 0;

^^

PS: vrai = 1 et faux = 0


59
Dans le cas où myBoolean représente une expression booléenne, l'utilisation de parenthèses est plus lisible.
rsp

40
Oui, comme dans (foo && (!bar || baz)) ? 1 : 0. Évidemment, s'il ne s'agit que d'un identifiant, les parens ne sont ni nécessaires ni souhaitables.
Blrfl

belle astuce avec booléen! Je cherchais peut-être un casting comme (int) true = 1, mais notant qu'il existe comme ceci: P
mumair

1
pour des débutants comme moi, ce (boolean expression) ? 1 : 0;serait plus compréhensible. Je pense que le mypréfixe l'a fait ressembler à une variable.
dixhom

12
@Blrfl dans vos exemples de parenthèses est un must , pas une question de lisibilité. foo && (!bar || baz) ? 1 : 0serait une erreur de syntaxe. (Je sais que ça fait 6 ans)
Konrad Morawski


59

L'utilisation de l'opérateur ternaire est la façon la plus simple, la plus efficace et la plus lisible de faire ce que vous voulez. Je vous encourage à utiliser cette solution.

Cependant, je ne peux pas résister à proposer une solution alternative, artificielle, inefficace et illisible.

int boolToInt(Boolean b) {
    return b.compareTo(false);
}

Hé, les gens aiment voter pour des réponses aussi cool!

Éditer

Soit dit en passant, j'ai souvent vu des conversions d'un booléen en un int dans le seul but de faire une comparaison des deux valeurs (généralement, dans les implémentations de compareTométhode). Boolean#compareToest la voie à suivre dans ces cas spécifiques.

Modifier 2

Java 7 a introduit une nouvelle fonction utilitaire qui fonctionne directement avec les types primitifs Boolean#compare(merci shmosel )

int boolToInt(boolean b) {
    return Boolean.compare(b, false);
}

1
Sera souligné par les JIT modernes, donc pas nécessairement inefficace. Il explique également pourquoi le b.compareTo est utilisé afin qu'il soit lisible.
Thorbjørn Ravn Andersen

2
Cela peut être lent car nous devons encadrer la valeur primitive dans un objet. La méthode de l'opérateur ternaire fonctionne directement avec des valeurs primitives sans conversion, donc je pense qu'elle est plus efficace.
barjak

5
1. Vous pouvez utiliser Boolean.compare()et éviter l'autoboxing. 2. La documentation de Boolean.compareTo()ne dit pas qu'elle renverra 1, seulement "une valeur positive si cet objet représente vrai et l'argument représente faux".
shmosel

1
Je viens de faire un test convertissant 1 000 000 de valeurs booléennes aléatoires et cette méthode était toujours plus rapide que celle basée sur l'opérateur ternaire. Il s'est rasé pendant environ 10 ms.
Mapsy

3
@AlexT. si vous faites des repères, vous devez utiliser un cadre pour vous assurer que vous mesurez correctement. Voir openjdk.java.net/projects/code-tools/jmh .
Thorbjørn Ravn Andersen

48
boolean b = ....; 
int i = -("false".indexOf("" + b));

14
Je pense que ce serait mieux adapté comme commentaire, pas comme réponse.
hpique

164
5 - b.toString().length
kennytm

5
@ ThorbjørnRavnAndersen Ouais. En utilisant l'une des autres méthodes publiées, plus efficaces, qui ne nécessitent pas cette surcharge. À moins que vous ne puissiez expliquer comment la création d'objets chaîne pour simplement vérifier la valeur d'un booléen est efficace.
b1nary.atr0phy

10
@ ThorbjørnRavnAndersen Je n'ai aucun contrôle sur la façon dont mes méthodes sont utilisées ou sur la fréquence à laquelle elles sont appelées, ce qui est tout à fait pertinent. Vous sacrifiez à la fois les performances et la lisibilité pour aucun avantage tangible.
b1nary.atr0phy

6
C'est certainement créatif mais je ne peux pas penser à un seul avantage à utiliser cette méthode. C'est plus verbeux et (je suppose) moins efficace, mais c'est certainement une méthode intéressante.
Mike Baxter

27
public int boolToInt(boolean b) {
    return b ? 1 : 0;
}

Facile


24
import org.apache.commons.lang3.BooleanUtils;
boolean x = true;   
int y= BooleanUtils.toInteger(x);

FWIW, BooleanUtils.toIntegerest implémenté comme juste return bool ? 1 : 0;.
Solomon Ucko

Apache Commons peut être utile, mais c'est tout simplement ridicule.
Eric Duminil

14

Cela dépend de la situation. Souvent, l'approche la plus simple est la meilleure car elle est facile à comprendre:

if (something) {
    otherThing = 1;
} else {
    otherThing = 0;
}

ou

int otherThing = something ? 1 : 0;

Mais il est parfois utile d'utiliser un Enum au lieu d'un drapeau booléen. Imaginons qu'il existe des processus synchrones et asynchrones:

Process process = Process.SYNCHRONOUS;
System.out.println(process.getCode());

En Java, enum peut avoir des attributs et des méthodes supplémentaires:

public enum Process {

    SYNCHRONOUS (0),
    ASYNCHRONOUS (1);

    private int code;
    private Process (int code) {
        this.code = code;
    }

    public int getCode() {
        return code;
    }
}

6
Une raison supplémentaire pour utiliser un if au lieu de ?:est que vous pouvez placer des points d'arrêt à l'intérieur des blocs if.
Thorbjørn Ravn Andersen

12

Si vous utilisez Apache Commons Lang (que je pense que beaucoup de projets l'utilisent), vous pouvez simplement l'utiliser comme ceci:

int myInt = BooleanUtils.toInteger(boolean_expression); 

toIntegerretourne 1 si boolean_expressionvrai, 0 sinon


FWIW, BooleanUtils.toIntegerest implémenté comme juste return bool ? 1 : 0;.
Solomon Ucko

8

Si true -> 1et la false -> 0cartographie est ce que vous voulez, vous pouvez faire:

boolean b = true;
int i = b ? 1 : 0; // assigns 1 to i.

6

Si vous voulez masquer, utilisez ceci:

System.out.println( 1 & Boolean.hashCode( true ) >> 1 );  // 1
System.out.println( 1 & Boolean.hashCode( false ) >> 1 ); // 0

3

Permet de jouer avec Boolean.compare(boolean, boolean). Comportement par défaut de la fonction: si les deux valeurs sont égales, elle renvoie 0sinon -1.

public int valueOf(Boolean flag) {
   return Boolean.compare(flag, Boolean.TRUE) + 1;
}

Explication : Comme nous le savons, le retour par défaut de Boolean.compare est -1 en cas de mauvaise correspondance, donc +1 donne une valeur de retour à 0 pour Falseet 1 pourTrue


3
Boolean.compare(myBoolean, false)conviendrait mieux à la description de la description
Vadzim

@Vadzim Oui va en effet générer 1 et 0 en comparant avec faux et dans le scénario actuel il va générer 0 et -1. Les deux solutions sont très bien et +1 pour votre commentaire :-)
mumair

0

Le fait que je doive écrire une méthode wrapper autour d'une instruction if pour convertir une valeur ne fait qu'ajouter à la liste déjà énorme des raisons pour lesquelles java devrait simplement mourir. Et voir l'opérateur ternaire même pas enveloppé dans une fonction mais juste copier-coller partout où je vois une distribution booléenne en int me rend fou. C'est un gaspillage de cycles CPU et une insulte à la lisibilité du code.

De plus, la plupart des réponses ici contiennent des centaines de votes positifs sans aucune explication, ce qui me fait deviner que les mauvaises pratiques sont simplement le résultat de l'exposition à Java. Si j'écrivais un opérateur ternaire pour lancer un booléen en int dans n'importe quelle langue moderne, je serais viré le lendemain de n'importe quel travail que j'aurais. Aujourd'hui, j'ai renoncé à essayer d'utiliser la raison avec mes missions Java et j'ai décidé d'embrasser la stupidité:

public static int booltoint(boolean nonsense) {
                                // Let's start with indenting using spaces, 16 of them to be precise
                                String[] ____int = new String[500];
                                ____int[0] = Boolean.toString(nonsense);
                                try {
                                                Thread.sleep(100); 
                                } catch (Exception e) {    }
                                Random rand = new Random();
                                int n = rand.nextInt((int)1e9);
                                int result = 0;
                                int other_Result = 1;
                                for (int i = -5; i < 2; i++) {
                                                try {
                                                                if (n == 35467247) return 5; // let's just fail with one in a billion chance
                                                                if ((5 - ____int[i].length()) == 1) {
                                                                                return ++result;
                                                                } else if(____int[i] == "false") {
                                                                                return --other_Result;
                                                                }
                                                } catch (Exception e) {
                                                                // This method will throw an exception 5 times every single time I 
                                                                // cast a boolean to int before returning an integer
                                                }
                                }
                                return (int)1e35;}

-1
public static int convBool(boolean b)
{
int convBool = 0;
if(b) convBool = 1;
return convBool;
}

Utilisez ensuite:

convBool(aBool);
En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.