Converti booleano in int in Java


350

Qual è il modo più accettato per convertire un booleanin intin Java?


8
A quali numeri pensi corrispondessero truee falserispettivamente?
Thorbjørn Ravn Andersen,

4
Alcune lingue hanno una conversione implicita da int a booleano. Java no. Tuttavia, l'implementazione ufficiale ha pacchetti SQL, e credo che questi convertano "false" in 0.
hpique

4
@Peter Lawrey Non se si desidera interagire con altri sistemi che non hanno valori booleani come tipo di dati non numerici.
hpique,

6
@Peter Lawrey La domanda non riguarda davvero la mappatura dei valori. Si tratta di come eseguire la conversione nel modo più chiaro e accettato.
hpique,

7
Tecnicamente, il compilatore Java definisce già una mappatura. True e False sono compilati rispettivamente a 1 e 0.
Antimonio,

Risposte:


583
int myInt = myBoolean ? 1 : 0;

^^

PS: true = 1 e false = 0


59
Nel caso in cui myBoolean rappresenti un'espressione booleana, l'uso della parentesi è più leggibile.
rsp,

40
Sì, come in (foo && (!bar || baz)) ? 1 : 0. Ovviamente, se si tratta solo di un identificatore, le parentesi non sono necessarie o desiderabili.
Blrfl,

bel trucco con booleano! Stavo guardando potrebbe esistere qualche casting come (int) true = 1, ma notando che esiste così: P
mumair,

1
per i principianti come me, (boolean expression) ? 1 : 0;sarebbe più comprensibile. Penso che il myprefisso lo abbia fatto sembrare una variabile.
Dixhom,

12
@Blrfl tra parentesi di esempio sono un must , non una questione di leggibilità. foo && (!bar || baz) ? 1 : 0sarebbe un errore di sintassi. (So ​​che sono passati 6 anni)
Konrad Morawski,


59

L'uso dell'operatore ternario è il modo più semplice, più efficiente e più leggibile per fare ciò che desideri. Ti incoraggio a usare questa soluzione.

Tuttavia, non posso resistere a proporre una soluzione alternativa, inventata, inefficiente, illeggibile.

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

Ehi, alla gente piace votare per risposte così interessanti!

modificare

A proposito, ho visto spesso conversioni da un booleano a un int al solo scopo di fare un confronto tra i due valori (generalmente, nelle implementazioni del compareTometodo).Boolean#compareToè la strada da percorrere in quei casi specifici.

Modifica 2

Java 7 ha introdotto una nuova funzione di utilità che funziona direttamente con i tipi primitivi, Boolean#compare(grazie shmosel )

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

1
Sarà sottolineato dalle moderne squadre investigative comuni, quindi non necessariamente inefficiente. Inoltre documenta il motivo per cui b.compareTo viene utilizzato, quindi è leggibile.
Thorbjørn Ravn Andersen,

2
Può essere lento perché dobbiamo racchiudere il valore di base in un oggetto. Il metodo dell'operatore ternario funziona direttamente con i valori primitivi senza conversione, quindi penso che sia più efficiente.
Barjak,

5
1. È possibile utilizzare Boolean.compare()ed evitare l'autoboxing. 2. La documentazione per Boolean.compareTo()non dice che restituirà 1, solo "un valore positivo se questo oggetto rappresenta vero e l'argomento rappresenta falso".
shmosel,

1
Ho appena fatto un test per convertire 1.000.000 di valori booleani casuali e questo metodo è stato costantemente più veloce di quello basato sull'operatore ternario. Si è rasato circa 10ms.
Mapsy,

3
@AlexT. se si eseguono microbenchmark, è necessario utilizzare un framework per assicurarsi di misurare correttamente. Vedi openjdk.java.net/projects/code-tools/jmh .
Thorbjørn Ravn Andersen,

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

14
Penso che questo sarebbe più adatto come commento, non come risposta.
hpique,

164
5 - b.toString().length
kennytm,

5
@ ThorbjørnRavnAndersen Sì. Utilizzando uno degli altri, più efficienti, metodi pubblicati che non richiedono quel sovraccarico. A meno che tu non possa spiegare in che modo la creazione di oggetti stringa per verificare semplicemente il valore di un valore booleano sia in qualche modo efficiente.
b1nary.atr0phy,

10
@ ThorbjørnRavnAndersen Non ho alcun controllo su come vengono utilizzati i miei metodi o sulla frequenza con cui vengono chiamati, il che è assolutamente il punto. Stai sacrificando sia le prestazioni che la leggibilità per nessun beneficio tangibile.
b1nary.atr0phy,

6
È decisamente creativo ma non riesco a pensare a un singolo vantaggio nell'uso di questo metodo. È più prolisso e (immagino) meno efficiente, ma è sicuramente un metodo interessante.
Mike Baxter,

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

semplice


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

FWIW, BooleanUtils.toIntegerè implementato come giusto return bool ? 1 : 0;.
Solomon Ucko,

Apache Commons può essere utile, ma questo è semplicemente ridicolo.
Eric Duminil,

14

Dipende dalla situazione. Spesso l'approccio più semplice è il migliore perché è facile da capire:

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

o

int otherThing = something ? 1 : 0;

Ma a volte è utile usare un Enum invece di una bandiera booleana. Immaginiamo che ci siano processi sincroni e asincroni:

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

In Java, enum può avere attributi e metodi aggiuntivi:

public enum Process {

    SYNCHRONOUS (0),
    ASYNCHRONOUS (1);

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

    public int getCode() {
        return code;
    }
}

6
Un ulteriore motivo per utilizzare un if anziché ?:è che è possibile inserire punti di interruzione all'interno dei blocchi if.
Thorbjørn Ravn Andersen,

12

Se usi Apache Commons Lang (che penso che molti progetti lo utilizzino), puoi semplicemente usarlo in questo modo:

int myInt = BooleanUtils.toInteger(boolean_expression); 

toIntegeril metodo restituisce 1 se boolean_expressionè vero, 0 altrimenti


FWIW, BooleanUtils.toIntegerè implementato come giusto return bool ? 1 : 0;.
Solomon Ucko,

8

Se true -> 1e la false -> 0mappatura è ciò che vuoi, puoi fare:

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

6

Se vuoi offuscare, usa questo:

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

3

Consente di giocare con Boolean.compare(boolean, boolean). Comportamento predefinito della funzione: se entrambi i valori sono uguali, 0altrimenti restituisce -1.

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

Spiegazione : Come sappiamo, il ritorno predefinito di Boolean.compare è -1 in caso di errata corrispondenza, quindi +1 porta il valore di ritorno a 0 per Falsee 1 perTrue


3
Boolean.compare(myBoolean, false)si adatterebbe meglio alla descrizione citata
Vadzim,

@Vadzim Sì infatti genererà 1 e 0 confrontando con false e nello scenario corrente genererà 0 e -1. Entrambe le soluzioni vanno bene e +1 per il tuo commento :-)
mumair

0

Il fatto che devo scrivere un metodo wrapper attorno a un'istruzione if per il cast di un valore si aggiunge alla già vasta lista di motivi per cui Java dovrebbe già morire. E vedendo l'operatore ternario non impacchettato nemmeno in una funzione, ma solo copiato incollato ovunque vedo un cast booleano che mi fa impazzire. È uno spreco di cicli di CPU e un insulto alla leggibilità del codice.

Inoltre la maggior parte delle risposte qui hanno centinaia di voti senza spiegazioni, il che mi fa supporre che le cattive pratiche siano solo il risultato dell'esposizione a java così tanto. Se avessi scritto un operatore ternario per aver lanciato il booleano in un linguaggio moderno, sarei stato licenziato il giorno successivo da qualsiasi lavoro avrei potuto avere. Quindi oggi ho smesso di provare a impiegare la ragione con i miei compiti di java e ho deciso di abbracciare 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;
}

Quindi utilizzare:

convBool(aBool);
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.