728x90
반응형
이항 연산자의 산술 연산자(쉬프트 연산자)에 대해 알아본다.

 

● 연산자는 크게 보면 단항 연산자, 이항 연산자, 삼항 연산자로 나뉘는데, 나뉘는 기준은 연산을 할 때 연산 대상이 되는 피 연산자의 개수가 몇 개냐가 기준이 된다.

따라서 피 연산자가 1개인 경우 단항 연산자, 2개인 경우 이항 연산자, 3개인 경우 삼항 연산자라고 생각하면 된다.

 

● 연산자는 연산을 하는 방향과, 여러 연산자가 같이 있을 때 어느 연산을 먼저 하는가 에 대한 연산 우선순위가 있으므로 아래 표를 참조하도록 하자.

예를 들어 「-2 + 3」이란 수식이 있다면 단항 연산자가 이항 연산자보다 우선순위가 높기 때문에 단항 연산자 중 하나인 부호 연산자가 2에 -1을 곱해 부호를 바꿔 -2를 만들고 그다음 -2와 3을 더하는 연산이 이항 연산자 중 하나인 사칙 연산자에 의해 이루어진다.

다만, 연산 순위가 잘 이해되지 않는다면 괄호를 적절히 사용해서 우선순위를 지정해 주는 것도 하나의 방법이 될 수 있다.

 

분류 연산자 연산방향 연산순위
 단항 연산자  증감 연산자  ++   -- 🡸 1
 부호 연산자  +   - 🡺
 비트전환 연산자  ~ 🡺
 논리부정 연산자  ! 🡺
 이항 연산자

 산술 연산자  나머지 연산자   % 🡺 2
 사칙 연산자 
 *   / 🡺
 +   -   🡺 3
 쉬프트 연산자  <<   >>   >>> 🡺 4
 비교 연산자  대소비교 연산자  <   >   <=   >=  instanceof 🡺 5
 등가비교 연산자  ==   != 🡺 6
 논리 연산자

 비트 연산자

 & 🡺 7
 ^ 🡺 8
 |  🡺 9
 논리 연산자
 && 🡺 10
 || 🡺 11
 그 외 연산자  삼항 연산자  ? : 🡺 12
 대입 연산자 (할당 연산자)  =   *=   /=   %=   +=   -=   <<=   >>=   >>>=   &=   |=   ^= 🡸 13

 

◆ 쉬프트 연산자 ( <<, >>,  >>>)


※ 쉬프트 연산자는 피 연산자를 2진수로 표현해서 각 자리를 왼쪽이나 오른쪽으로 이동하는 연산자로, 정수형 변수에만 사용 가능하다.

※ 사칙 연산자인 곱셈「*과 나눗셈「/」 보다 연산 속도가 빠른 장점이 있지만 코드의 가독성이 떨어지는 단점도 있다.

 x << n  피연산자 x의 값을 2진수로 표현한뒤 부호에 상관없이 각자리를 왼쪽으로 n번 이동한다.
 이동으로 인한 빈 자리는 0으로 채운다.
 결과값은 결국「x 곱하기 2ⁿ과 같다.
<< 2진수로 표현   0 0 0 0 0 1 1 1
지정한 횟수만큼 2진수 값을 왼쪽으로 이동, 밀려난 왼쪽을 버림 0 0 0 0 0 1 1 1  
왼쪽을 버린 만큼 오른쪽 빈자리에 0을 채워줌   0 0 0 0 1 1 1 0
<< 예제
10 (2진수 표현)

⇒      [00000000 00000000 00000000 00001010]
10 << 0 (10을 2진수로 표현한 뒤 각 자리를 왼쪽으로 0번 이동 「 이동 없음」)
⇒      [00000000 00000000 00000000 00001010]
10 << 1 (10을 2진수로 표현한 뒤 각 자리를 왼쪽으로 1번 이동「 오른쪽 빈자리는 0으로 채움」)
⇒  0  [00000000 00000000 00000000 00010100]
10 << 2 (10을 2진수로 표현한뒤 각 자리를 왼쪽으로 2번 이동「 오른쪽 빈자리는 0으로 채움」)
00 [00000000 00000000 00000000 00101000]
-10 (2진수)
⇒       [11111111 11111111 11111111 11110110]
-10 << 0 (-10을 2진수로 표현한뒤 각 자리를 왼쪽으로 0번 이동「 이동 없음」)
⇒       [11111111 11111111 11111111 11110110]
-10 << 1 (-10을 2진수로 표현한 뒤 각 자리를 왼쪽으로 1번 이동「 오른쪽 빈자리는 0으로 채움」)
⇒  1  [11111111 11111111 11111111 11101100]
-10 << 2 (-10을 2진수로 표현한뒤 각 자리를 왼쪽으로 2번 이동「 오른쪽 빈자리는 0으로 채움」)
11 [11111111 11111111 11111111 11011000]

 x >> n  피연산자 x의 값을 2진수로 표현한뒤 각자리를 오른쪽으로 n번 이동한다.
 피연산자가 양수인경우, 이동으로 인한 빈 자리는 0으로 채운다.
 피연산자가 음수인경우, 부호 유지를 위해 이동으로 인한 빈 자리는 1로 채운다.
 결과값은 결국「x 나누기 2ⁿ과 같다.
>> 2진수로 표현 0 0 0 0 0 1 1 1  
지정한 횟수만큼 2진수 값을 오른쪽으로 이동, 밀려난 오른쪽을 버림   0 0 0 0 0 1 1 1
오른쪽을 버린만큼 왼쪽 빈자리에 0 또는 1을 채워줌 0 0 0 0 0 0 1 1  

 

>> 예제
10 (2진수 표현)

⇒ [00000000 00000000 00000000 00001010]
10 >> 0 (10을 2진수로 표현한뒤 각 자리를 오른쪽으로 0번 이동 「 이동 없음」)
⇒ [00000000 00000000 00000000 00001010]
10 >> 1 (10을 2진수로 표현한 뒤 각 자리를 오른쪽으로 1번 이동「 왼쪽 빈자리는 0으로 채움」)
⇒ [00000000 00000000 00000000 00000101] 0
10 >> 2 (10을 2진수로 표현한뒤 각 자리를 오른쪽으로 2번 이동「 왼쪽 빈자리는 0으로 채움」)
⇒ [00000000 00000000 00000000 00000010] 10
-10 (2진수)
⇒ [11111111 11111111 11111111 11110110]
-10 >> 0 (-10을 2진수로 표현한뒤 각 자리를 오른쪽으로 0번 이동 「 이동 없음」)
⇒ [11111111 11111111 11111111 11110110]
-10 >> 1 (-10을 2진수로 표현한 뒤 각 자리를 오른쪽으로 1번 이동「 왼쪽 빈자리는 1로 채움」)
⇒ [11111111 11111111 11111111 11111011] 0
-10 >> 2 (-10을 2진수로 표현한 뒤 각 자리를 오른쪽으로 2번 이동「 왼쪽 빈자리는 1로 채움」)
⇒ [11111111 11111111 11111111 11111101] 10

 x >>> n  피연산자 x의 값을 2진수로 표현한뒤 각자리를 오른쪽으로 n번 이동한다.
 피연산자의 부호 상관없이, 이동으로 인한 빈 자리는 무조건 0으로 채운다.
 피연산자x가 양수인 경우 결과값은 결국「x 나누기 2ⁿ과 같지만 피연산자x가 음수의 경우는 빈자리를
 부호 상관없이 무조건 0으로 채우기 때문에 x 나누기 2ⁿ」의 결과값이 나오지 않는다.

>>> 2진수로 표현 0 0 0 0 0 1 1 1  
지정한 횟수만큼 2진수 값을 오른쪽으로 이동, 밀려난 오른쪽을 버림   0 0 0 0 0 1 1 1
오른쪽을 버린만큼 왼쪽 빈자리에 1을 채워줌 0 0 0 0 0 0 1 1  
>>> 예제
10 (2진수 표현)

⇒ [00000000 00000000 00000000 00001010]
10 >>> 0 (10을 2진수로 표현한 뒤 각 자리를 오른쪽으로 0번 이동 「 이동 없음」)
⇒ [00000000 00000000 00000000 00001010]
10 >>> 1 (10을 2진수로 표현한 뒤 각 자리를 오른쪽으로 1번 이동「 왼쪽 빈자리는 0으로 채움」)
⇒ [00000000 00000000 00000000 00000101] 0
10 >>> 2 (10을 2진수로 표현한뒤 각 자리를 오른쪽으로 2번 이동「 왼쪽 빈자리는 0으로 채움」)
⇒ [00000000 00000000 00000000 00000010] 10
-10 (2진수)
⇒ [11111111 11111111 11111111 11110110]
-10 >>> 0 (-10을 2진수로 표현한뒤 각 자리를 오른쪽으로 0번 이동 「 이동 없음」)
⇒ [11111111 11111111 11111111 11110110]
-10 >>> 1 (-10을 2진수로 표현한 뒤 각 자리를 오른쪽으로 1번 이동「 왼쪽 빈자리는 0으로 채움」)
⇒ [01111111 11111111 11111111 11111011] 0
-10 >>> 2 (-10을 2진수로 표현한뒤 각 자리를 오른쪽으로 2번 이동「 왼쪽 빈자리는 0으로 채움」)
⇒ [00111111 11111111 11111111 11111101] 10

● 자바에서 정수의 2진수 값을 확인할때는 Integer.toBinaryString() 메서드를 이용하여 10진수 int 형식의 값을 2진수의 String문자로 변환하여 확인할 수 있다.

10진수 ⇒ 2진수 변환: Java.lang.Integer.toBinaryString()

10진수 ⇒ 8진수 변환: Java.lang.Integer.toOctalString()

10진수 ⇒ 16진수 변환: Java.lang.Integer.toHexString()

//Integer.toBinaryString()메서드로 2진수(쉬프트 연산결과)값을 확인하는 예제
System.out.println(Integer.toBinaryString(10)); //출력값: 1010

System.out.println(Integer.toBinaryString(10<<0)); //출력값: 1010
System.out.println(Integer.toBinaryString(10<<1)); //출력값: 10100
System.out.println(Integer.toBinaryString(10<<2)); //출력값: 101000

System.out.println(Integer.toBinaryString(10>>0)); //출력값: 1010
System.out.println(Integer.toBinaryString(10>>1)); //출력값: 101
System.out.println(Integer.toBinaryString(10>>2)); //출력값: 10

System.out.println(Integer.toBinaryString(10>>>0)); //출력값: 1010
System.out.println(Integer.toBinaryString(10>>>1)); //출력값: 101
System.out.println(Integer.toBinaryString(10>>>2)); //출력값: 10

System.out.println(Integer.toBinaryString(-10)); //출력값: 11111111111111111111111111110110

System.out.println(Integer.toBinaryString(-10<<0)); //출력값: 11111111111111111111111111110110
System.out.println(Integer.toBinaryString(-10<<1)); //출력값: 11111111111111111111111111101100
System.out.println(Integer.toBinaryString(-10<<2)); //출력값: 11111111111111111111111111011000

System.out.println(Integer.toBinaryString(-10>>0)); //출력값: 11111111111111111111111111110110
System.out.println(Integer.toBinaryString(-10>>1)); //출력값: 11111111111111111111111111111011
System.out.println(Integer.toBinaryString(-10>>2)); //출력값: 11111111111111111111111111111101

System.out.println(Integer.toBinaryString(-10>>>0)); //출력값: 11111111111111111111111111110110
System.out.println(Integer.toBinaryString(-10>>>1)); //출력값: 1111111111111111111111111111011
System.out.println(Integer.toBinaryString(-10>>>2)); //출력값: 111111111111111111111111111101

 


글 내용 중 잘못된 부분이 있거나, 첨부하실 내용이 있으시면 댓글로 남겨주세요. 공부하는데 많은 도움이 됩니다.
-- 기억의 유효기간은 생각보다 짧다. --

 

728x90
반응형