2010-10-11 7 views
106

Funktioniert der Operator Java & = & & &&?

boolean a = false; 

Ich habe mich gefragt Unter der Annahme, wenn tun:

a &= b; 

zu

a = a && b; //logical AND, a is false hence b is not evaluated. 

oder auf der anderen Seite

bedeutet dies entspricht
a = a & b; //Bitwise AND. Both a and b are evaluated. 

Antwort

111

Aus der Java Language Specification - 15.26.2 Compound Assignment Operators.

Verbindung Zuweisungsausdruck von der Form E1 op= E2 entspricht E1 = (T)((E1) op (E2)), wobei die Art der TE1 ist, mit der Ausnahme, dass E1 nur einmal ausgewertet wird.

So a &= b; entspricht a = a & b;.

(In einigen Verwendungen macht das Typ-Casting einen Unterschied zu dem Ergebnis, aber in diesem b hat boolean und die Art Guss tut nichts.)


In der Praxis gibt es kleiner Unterschied zwischen a = a & b; und a = a && b;. Wenn b eine Variable oder eine Konstante ist, wird das Ergebnis für beide Versionen gleich sein. Es gibt nur einen semantischen Unterschied, wenn die Auswertung von b Nebenwirkungen haben kann; d.h. wenn es sich um einen nicht-trivialen Unterausdruck handelt.

Auf der Leistungsseite ist der Kompromiss zwischen den Kosten b auszuwerten, und die Kosten für einen Test und Zweig des Wertes von a und die mögliche Einsparung von eine unnötige Zuordnung zu a zu vermeiden. Die Analyse ist nicht einfach, aber wenn die Kosten für die Berechnung b nicht trivial sind, ist der potenzielle Leistungsunterschied zwischen den beiden Versionen wahrscheinlich zu gering, um eine Überlegung wert zu sein.

19

Es ist die letzte:

a = a & b; 
30

siehe 15.22.2 of the JLS. Für boolesche Operanden ist der Operator & boolesch, nicht bitweise. Der einzige Unterschied zwischen && und & für boolesche Operanden besteht darin, dass dieser für && kurzgeschlossen ist (was bedeutet, dass der zweite Operand nicht ausgewertet wird, wenn der erste Operand falsch ist).

Also in Ihrem Fall, wenn b ein primitiv, a = a && b, a = a & b und a &= b alle das gleiche tun.

+1

So (a &= b;) wird nicht kurzgeschlossen werden, wenn b ein Methodenaufruf ist? Gibt es so etwas wie einen "&& =" Operator? – is7s

+1

korrekt. b() wird aufgerufen. Es gibt keinen && = Operator. – stew

+1

Es scheint, dass dies die Frage nicht beantwortet; Das OP wusste bereits von Kurzschluss. –

0

Ich stieß auf eine ähnliche Situation mit booleans, wo ich vermeiden wollte, b() zu nennen, wenn a bereits falsch war.

Das ist für mich gearbeitet:

a &= a && b() 
+21

Um Redundanzen zu vermeiden (immer noch Kurzschlüsse möglich), können Sie einfach 'a = a && b()' schreiben. –