2011-04-06 39 views
107

Siempre pensé que el operador && en Java se usa para verificar si sus dos operandos booleanos son true, y el operador & se usa para realizar operaciones de bits en dos tipos enteros.Diferencia entre & y &

Recientemente me enteré de que el operador & también se puede usar para verificar si sus dos operandos booleanos son true, la única diferencia es que comprueba el operando RHS incluso si el operando LHS es falso.

¿Está el operador & en Java internamente sobrecargado? ¿O hay algún otro concepto detrás de esto?

+3

duplicado posible de [¿Por qué suelen utilizar \ '|| \' 'no \ |? \ ', ¿Cuál es la diferencia] (http://stackoverflow.com/questions/7101992/why-do -we-usually-use-not-what-is-the-difference) –

+0

Doble atajo de acceso directo si es posible. –

Respuesta

191

& < - verifica ambos operandos
& & < - detiene evaluar si el primer operando se evalúa como falsa ya que el resultado será falsa

(x != 0) & (1/x > 1) < - esto significa evaluar (x != 0) luego evaluar (1/x > 1) luego haga el &. el problema es que para x = 0 esto generará una excepción.

(x != 0) && (1/x > 1) < - esto significa evaluar (x != 0) y sólo si esto es cierto entonces evaluar (1/x > 1) por lo que si usted tiene x = 0, entonces esto es perfectamente seguro y no arrojar alguna excepción si se evalúa como falsa (x = 0) todo el asunto se evalúa como falso sin evaluar el (1/x > 1).

EDIT:

exprA | exprB < - esto significa evaluar exprA luego evaluar exprB luego hacer el |.

exprA || exprB < - esto significa evaluar exprA y sólo si se trata de evaluar falseexprB y hacer el ||.

+2

¿Cuál es el motivo para escribir uno y/o | en la declaración if? Nunca será más rápido que && y ||. ¿Por qué queremos verificar una segunda condición si ya podemos tener una respuesta? ¿Puede proporcionar un ejemplo realista, por favor? – Michu93

+5

@ Michu93: Un ejemplo sería si la segunda condición es una llamada a función que tiene un efecto secundario que siempre necesita. Dado que los efectos secundarios generalmente deberían evitarse, solo habrá casos raros en los que lo necesite, y no puedo pensar en un ejemplo realista en este momento. – Heinzi

25
boolean a, b; 

Operation  Meaning      Note 
---------  -------      ---- 
    a && b  logical AND     short-circuiting 
    a || b  logical OR      short-circuiting 
    a & b  boolean logical AND   not short-circuiting 
    a | b  boolean logical OR    not short-circuiting 
    a^b  boolean logical exclusive OR 
    !a   logical NOT 

short-circuiting  (x != 0) && (1/x > 1) SAFE 
not short-circuiting (x != 0) & (1/x > 1) NOT SAFE 
+0

Gracias Andreas por la edición, tal vez esta otra pregunta también sea útil: http://stackoverflow.com/questions/4014535/vs-and-vs – Torres

9

Depende del tipo de los argumentos ...

Para argumentos enteros, el único signo ("&") es el operador 'AND de bits'. El doble ampersand ("& &") no está definido para nada que no sean dos argumentos booleanos.

Para argumentos booleanos, el símbolo comercial único constituye el operador "lógico AND" (incondicional) mientras que el signo doble ("& &") es el operador "condicional Y lógico". Es decir que el signo único siempre evalúa ambos argumentos, mientras que el signo doble solo evaluará el segundo argumento si el primer argumento es verdadero.

Para todos los demás tipos de argumentos y combinaciones, debe producirse un error en tiempo de compilación.

7

& & es un operador de cortocircuito mientras que & es un operador AND.

Pruebe esto.

String s = null; 
    boolean b = false & s.isEmpty(); // NullPointerException 
    boolean sb = false && s.isEmpty(); // sb is false 
5

es como se especifica en el JLS (15.22.2):

Cuando ambos operandos de un &, ^, o | operador son de tipo booleano o booleano, entonces el tipo de expresión de operador bit a bit es booleano. En todos los casos, los operandos están sujetos a la conversión de unboxing (§5.1.8) según sea necesario.

Para &, el valor del resultado es verdadero si ambos valores del operando son verdaderos; de lo contrario, el resultado es falso.

Para ^, el valor del resultado es verdadero si los valores del operando son diferentes; de lo contrario, el resultado es falso.

Para |, el valor del resultado es falso si ambos valores del operando son falsos; de lo contrario, el resultado es verdadero.

El "truco" es que & es un número entero bit a bit operador así como un Operador lógico booleano . Entonces, ¿por qué no? Ver esto como un ejemplo para sobrecarga del operador es razonable.

35

Además de no ser un evaluador vago mediante la evaluación de los dos operandos, creo que las principales características de los operadores de bits comparar cada bytes de operandos como en el siguiente ejemplo:

int a = 4; 
int b = 7; 
System.out.println(a & b); // prints 4 
//meaning in an 32 bit system 
// 00000000 00000000 00000000 00000100 
// 00000000 00000000 00000000 00000111 
// =================================== 
// 00000000 00000000 00000000 00000100 
+0

La pregunta es sobre operaciones lógicas booleanas, no operaciones bit a bit. – EJP

+5

@EJP Ayuda aún a los googlers como yo, que solo leen el título. –

3

Con booleanos, no hay diferencia de salida entre los dos. Puede cambiar & & y & o || y | y nunca cambiará el resultado de tu expresión.

La diferencia radica en la escena donde se procesa la información. Al hacer una expresión "(a = 0) & (b = 0)" para a = 0 y b = 1, ocurre lo siguiente:

left side: a != 0 --> false 
right side: b 1= 0 --> true 
left side and right side are both true? --> false 
expression returns false 

Cuando se escribe una expresión (a != 0) && (b != 0) cuando a = 0 y b = 1, ocurre lo siguiente:

a != 0 -->false 
expression returns false 

menos pasos, menos procesamiento, mejor codificación, especialmente cuando se hace muchos expresión booleana o argumentos complicados.

+2

Cambiará el resultado general de la expresión si los operandos tienen efectos secundarios. – EJP

4

'& &': - es un operador lógico AND produce un valor booleano de verdadero o falso en función de la relación lógica de sus argumentos.

Por ejemplo: - Condición1 & & Condición2

Si Condición1 es falsa, entonces (Condición1 & & Condición2) siempre será falsa, que es la razón por la cual este operador lógico es también conocido como Short operador Circuito porque no evalúa otra condición. Si Condition1 es falso, entonces no hay necesidad de evaluar Condtiton2.

Si Condition1 es verdadero, se evalúa Condition2, si es verdadero, entonces el resultado general será verdadero, de lo contrario será falso.

'&': - es un operador Y de Bitwise. Produce uno (1) en la salida si ambos bits de entrada son uno. De lo contrario, produce cero (0).

Por ejemplo: -

int a = 12; // la representación binaria de 12 es 1100

int b = 6; // la representación binaria de 6 es 0110

int c = (a & b); // representación binaria de (12 & 6) es 0100

El valor de c es 4.

para la referencia, consulte esta http://techno-terminal.blogspot.in/2015/11/difference-between-operator-and-operator.html

4

&& y || son llamados operadores de corto circuito. Cuando se usan, para || - si el primer operando se evalúa como true, entonces el resto de los operandos no se evalúan. Para && - si el primer operando se evalúa como false, el resto de ellos no se evalúa en absoluto.

if (a || (++x > 0)) En este ejemplo, la variable x no se incrementará si a era true.

0

& es un operador bit a bit más utilizado para verificar ambas condiciones porque a veces tenemos que evaluar ambas condiciones. Pero el operador lógico & & pasa a la 2ª condición cuando la primera condición da verdadero.

0

todas las respuestas son great, y parece que no más respuesta is needed pero acabo acostumbrada a señalar algo sobre && operador llama dependent condition

En expresiones usando el operador & &, una llamada condición-nosotros este el dependent condition -puede requerir que otra condición sea verdadera para que la evaluación de la condición dependiente sea significativa.

En este caso, la condición dependiente se debe colocar después del operador & & para evitar errores.

Considere la expresión (i != 0) && (10/i == 2). La condición dependiente (10/i == 2) debe appear after el operador && para evitar la posibilidad de división por cero.

otro ejemplo (myObject != null) && (myObject.getValue() == somevaluse)

y otra cosa: && y || son llamados short-circuit evaluation porque el segundo argumento se ejecuta o evaluó only if el argumento first hace not suffice-determine la value de los expression

Referencias: Java™ How To Program (Early Objects), Tenth Edition

7

Creo que mi respuesta puede ser más comprensible:

Hay dos diferencias entre & y &&.

Si utilizan como lógica Y

& y && puede ser lógico AND, cuando el & o && izquierda y derecha resultado de la expresión es verdad todo, todo el resultado de la operación puede ser verdad.

cuando & y && tan lógico AND, hay una diferencia:

cuando el uso && tan lógico AND, si el resultado de la expresión es falsa izquierda, la expresión de la derecha no se ejecutará.

Tomemos el ejemplo:

String str = null; 

if(str!=null && !str.equals("")){ // the right expression will not execute 

} 

Si se utiliza &:

String str = null; 

if(str!=null & !str.equals("")){ // the right expression will execute, and throw the NullPointerException 

} 

Un otro ejemplo más:

int x = 0; 
int y = 2; 
if(x==0 & ++y>2){ 
    System.out.print(“y=”+y); // print is: y=3 
} 

int x = 0; 
int y = 2; 
if(x==0 && ++y>2){ 
    System.out.print(“y=”+y); // print is: y=2 
} 

& se puede utilizar como operador de bits

& se puede utilizar como bit a bit AND operador, && no puede.

El AND bit a bit "&" operador produce 1 si y sólo si tanto de los bits en sus operandos son 1. Sin embargo, si tanto de los bits son 0 o ambos de los bits son diferentes, entonces este operador produce 0. Para ser más preciso a nivel de bit y "&" devuelve 1 operador si alguno de los dos bits es 1 y devuelve 0 si cualquiera de los bits es 0.

Desde la página wiki:

http://www.roseindia.net/java/master-java/java-bitwise-and.shtml

1

Además de & & y || Al estar en cortocircuito, también considere la precedencia del operador cuando mezcle las dos formas. Creo que no será inmediatamente evidente para todos que el resultado1 y el resultado2 contienen valores diferentes.

boolean a = true; 
boolean b = false; 
boolean c = false; 

boolean result1 = a || b && c; //is true; evaluated as a || (b && c) 
boolean result2 = a | b && c; //is false; evaluated as (a | b) && c