2009-11-12 6 views
87

Les opérateurs bit à bit sont supposés déplacer des variables et les exploiter bit à bit. Dans le cas des entiers, des longs, des caractères, cela a du sens. Ces variables peuvent contenir toute la gamme de valeurs imposées par leur taille.Effet d'un opérateur bit à bit sur un booléen en Java

Dans le cas des booléens, cependant, un booléen ne peut contenir que deux valeurs. 1 = vrai ou 0 = faux. Mais la taille du booléen n'est pas définie. Il peut être aussi gros qu'un octet ou un petit peu.

Alors, quel est l'effet de l'utilisation d'un opérateur bitwise sur un booléen? La JVM la traduit-elle essentiellement par un opérateur logique normal et passe-t-elle à autre chose? Traite-t-il le booléen comme une entité binaire unique dans le but de l'opération? Ou le résultat est-il indéfini avec la taille d'un booléen?

+0

Je pense que vous ne pouvez pas utiliser un opérateur au niveau du bit sur un booléen. Seulement sur les nombres. Je suis sûr que ~ ne fonctionnera pas, je ne sais pas ce qu'il en est des autres opérateurs. –

+4

Vous pouvez utiliser certains d'entre eux, nous venons de découvrir un | utilisé dans notre code existant. Nous l'enlevons, mais ce code a été compilé et a fonctionné. –

+9

Puisque l'un est en court-circuit et l'autre non (voir la réponse de mobrule), avant de changer le | à || vous pouvez vous assurer que les expressions booléennes suivantes n'ont aucun effet secondaire que le programmeur d'origine a l'intention de toujours exécuter. –

Répondre

91

Les opérateurs &,^et | sont des opérateurs au niveau du bit lorsque les opérandes sont des types entiers primitifs. Ce sont des opérateurs logiques lorsque les opérandes sont booléens, et leur comportement dans le dernier cas est spécifié. Voir la section 15.22.2 du Java Language Specification pour plus de détails.

+38

Plus précisément, & et^et | sont les opérateurs booléens logiques sans court-circuit. – Ken

+12

Voici un lien direct vers la section susmentionnée: http://docs.oracle.com/javase/specs/jls/se7/html/jls-15.html#jls-15.22.2 –

+0

Si ce qui précède est vrai, pourquoi? est http://ideone.com/oGSF7c lançant une exception de pointeur nul? Si l'opérateur '| =' était logique, le programme n'aurait jamais dû exécuter la directive 'x.getValue()'. – ikromm

70

Utilisation de l'opérateur au niveau du bit peut contourner le comportement court-circuit:

boolean b = booleanExpression1() && booleanExpression2(); 
boolean b = booleanExpression1() & booleanExpression2(); 

Si booleanExpression1() évalue à false, puis
booleanExpression2() n'est pas évalué dans le premier cas, et
booleanExpression2() (et quels que soient les effets secondaires il peut avoir) est évalué dans le deuxième cas,

+2

Et l'opération bitwise effectue généralement [plus rapide que le court-circuit un] (http://stackoverflow.com/a/3076091/94363) (à condition que l'évaluation soit simple) – rds

+0

Le 'bit' sera 'plus rapide, mais le appel à la deuxième fonction pourrait être ignoré avec l'utilisation de '&&' – NatNgs

15

Au-delà de ce qui est couvert dans les autres réponses, c'est wo Remarquez que && et || ont une priorité différente de & et |.

Extrait de the precedence table (avec la plus haute priorité en haut).

bitwise AND     & 
bitwise exclusive OR  ^
bitwise inclusive OR  | 
logical AND     && 
logical OR     || 

Qu'est-ce que cela signifie pour vous?

Absolument rien, aussi longtemps que vous tenez soit seulement & et | ou seulement && et ||. Mais, puisque | a une plus haute précision que && (par opposition à ||, qui a une priorité inférieure), en les mélangeant librement pourrait conduire à un comportement inattendu.

Alors a && b | c && d est le même que a && (b | c) && d,
par opposition à a && b || c && d qui serait (a && b) || (c && d).

Pour prouver qu'ils ne sont pas les mêmes, envisager un extrait de la table de vérité:

a | b | c | d | (b|c) | (a&&b) | (c&&d) | a && (b|c) && d | (a&&b) || (c&&d) 
F | T | T | T | T | F | T |   F  |  T 
               ^   ^
                |- not the same -| 

Si vous voulez ou avoir une priorité plus élevée que ET, vous pourrait utiliser | et && ensemble, mais ce n'est pas recommandé.

Mais vous devriez vraiment les mettre entre parenthèses pour clarifier la priorité à chaque fois que l'utilisation de symboles différents, à savoir (a && b) || c (entre parenthèses pour clarifier la priorité), a && b && c (pas de crochets nécessaires).

Questions connexes