java - switch - Diferencia entre>>> y>>
unary operators java (7)
Ambos son a la derecha, pero >>>
está unsigned
De la documentation :
El operador de cambio a la derecha sin signo ">>>" desplaza un cero a la posición más a la izquierda, mientras que la posición más a la izquierda después de ">>" depende de la extensión de la señal.
¿Cuál es la diferencia entre los operadores >>>
y >>
en Java?
El desplazamiento lógico hacia la derecha ( v >>> n
) devuelve un valor en el que los bits en v
se han desplazado hacia la derecha por n
posiciones de bit, y los 0 se desplazan desde el lado izquierdo. Considere cambiar los valores de 8 bits, escritos en binario:
01111111 >>> 2 = 00011111
10000000 >>> 2 = 00100000
Si interpretamos los bits como un entero no negativo sin signo, el desplazamiento lógico hacia la derecha tiene el efecto de dividir el número por la potencia correspondiente de 2. Sin embargo, si el número está en la representación de dos complementos, el desplazamiento lógico hacia la derecha no divide correctamente los números negativos . Por ejemplo, el segundo desplazamiento a la derecha anterior cambia de 128 a 32 cuando los bits se interpretan como números sin signo. Pero cambia de -128 a 32 cuando, como es típico en Java, los bits se interpretan en el complemento de dos.
Por lo tanto, si está cambiando para dividir por una potencia de dos, desea el desplazamiento aritmético a la derecha ( v >> n
). Devuelve un valor en el que los bits en v
se han desplazado hacia la derecha por n
posiciones de bit, y las copias del bit más a la izquierda de v se desplazan desde el lado izquierdo:
01111111 >> 2 = 00011111
10000000 >> 2 = 11100000
Cuando los bits son un número en la representación del complemento a dos, el desplazamiento a la derecha aritmética tiene el efecto de dividir por una potencia de dos. Esto funciona porque el bit más a la izquierda es el bit de signo. La división por una potencia de dos debe mantener el signo igual.
El operador lógico de desplazamiento a la derecha ( >>> N
) desplaza los bits hacia la derecha en las posiciones N, descartando el bit de signo y rellenando los N de los bits más a la izquierda con 0. Por ejemplo:
-1 (in 32-bit): 11111111111111111111111111111111
después de una operación >>> 1
convierte en:
2147483647: 01111111111111111111111111111111
El operador aritmético de desplazamiento a la derecha ( >> N
) también desplaza los bits hacia la derecha en las posiciones N, pero conserva el bit de signo y rellena los N bits más a la izquierda con 1. Por ejemplo:
-2 (in 32-bit): 11111111111111111111111111111110
después de una operación >> 1
convierte en:
-1: 11111111111111111111111111111111
Lea más acerca de los operadores Bitwise y Bit Shift
>> Signed right shift
>>> Unsigned right shift
El patrón de bits viene dado por el operando de la izquierda, y el número de posiciones a desplazar por el operando de la derecha. El operador de cambio a la derecha sin signo >>>
desplaza un cero a la posición más a la izquierda ,
mientras que la posición más a la izquierda después de >>
depende de la extensión de signo.
En palabras simples >>>
siempre desplaza un cero a la posición más a la izquierda, mientras que >>
cambia en función del signo del número, es decir, 1 para el número negativo y 0 para el número positivo.
Por ejemplo, trate con números negativos y positivos.
int c = -153;
System.out.printf("%32s%n",Integer.toBinaryString(c >>= 2));
System.out.printf("%32s%n",Integer.toBinaryString(c <<= 2));
System.out.printf("%32s%n",Integer.toBinaryString(c >>>= 2));
System.out.println(Integer.toBinaryString(c <<= 2));
System.out.println();
c = 153;
System.out.printf("%32s%n",Integer.toBinaryString(c >>= 2));
System.out.printf("%32s%n",Integer.toBinaryString(c <<= 2));
System.out.printf("%32s%n",Integer.toBinaryString(c >>>= 2));
System.out.printf("%32s%n",Integer.toBinaryString(c <<= 2));
salida:
11111111111111111111111111011001
11111111111111111111111101100100
111111111111111111111111011001
11111111111111111111111101100100
100110
10011000
100110
10011000
>>>
es unsigned-shift; insertará 0. >>
está firmado, y extenderá el bit de signo.
JLS 15.19 Operadores de Turno
Los operadores de cambio incluyen el desplazamiento a la izquierda
<<
, el desplazamiento a la derecha firmado, y el desplazamiento a la derecha sin signo>>>
.El valor de
n>>s
esn
posiciones de bit de desplazamiento hacias
derecha con extensión de signo .El valor de
n>>>s
esn
posiciones de bit de desplazamiento hacias
derecha con extensión cero .
System.out.println(Integer.toBinaryString(-1));
// prints "11111111111111111111111111111111"
System.out.println(Integer.toBinaryString(-1 >> 16));
// prints "11111111111111111111111111111111"
System.out.println(Integer.toBinaryString(-1 >>> 16));
// prints "1111111111111111"
Para aclarar las cosas agregando contrapartida positiva.
System.out.println(Integer.toBinaryString(121));
// prints "1111001"
System.out.println(Integer.toBinaryString(121 >> 1));
// prints "111100"
System.out.println(Integer.toBinaryString(121 >>> 1));
// prints "111100"
Como es positivo, tanto los turnos firmados como los no firmados agregarán 0 a la parte más izquierda.
Preguntas relacionadas
- Cambio a la derecha para realizar la división por 2 en -1
- ¿Está cambiando bits más rápido que multiplicar y dividir en Java? .¿RED?
- ¿Cuál es la forma equivalente de c / c ++ de hacer ''>>>'' como en java (desplazamiento a la derecha sin signo)
- Cambio lógico negativo
- ¿El operador >> versus >>> de Java?
- ¿Cuál es la diferencia entre los operadores de Java >> y >>>?
- Diferencia entre los operadores >>> y >>
- ¿Cuál es la razón por la que los lenguajes de alto nivel como C # / Java enmascaran el operando de conteo de desplazamiento de bits?
-
1 >>> 32 == 1
-
>>>
siempre pondrá un 0 en el bit más a la izquierda, mientras que >>
pondrá un 1 o un 0 dependiendo de cuál sea su signo.
>>
es el cambio aritmético a la derecha, >>>
es el cambio lógico a la derecha.
En un cambio aritmético, el bit de signo se extiende para preservar la firmeza del número.
Por ejemplo: -2 representado en 8 bits sería 11111110
(porque el bit más significativo tiene un peso negativo). Desplazándolo hacia la derecha un bit usando el cambio aritmético le daría 11111111
, o -1. El cambio lógico hacia la derecha, sin embargo, no le importa que el valor pueda representar un número firmado; simplemente mueve todo a la derecha y rellena desde la izquierda con 0s. Cambiar nuestro -2 a la derecha con un cambio lógico daría 01111111
.