주인장의 프로그래밍 개발 공부방

[Chapter 2 연산자] 6. 비트 연산자 - 시프트 연산자 (Shift Operator) 본문

프로그래밍 기본 지식/Chapter 2 연산자

[Chapter 2 연산자] 6. 비트 연산자 - 시프트 연산자 (Shift Operator)

거신 2019. 5. 20. 21:39

지금까지 다양한 연산자들에 대해서 알아보고 있다.

연산자의 종류는 엄청나게 다양하지만

의외로 우리들이 알고 있는 연산자들도 많고

생각보다 쉬운 연산자들도 더러 있었다.

그런데 이번 시간에는 조금은 생소한, 아니 아예 처음 본 연산자에다가

계산하는 과정조차 희한한 연산자를 알아보려 한다.

그렇다고 어려운 녀석은 아니니 걱정은 하지말자.

 

목표 : 시프트 연산자를 이용해서 비트 이동을 할 수 있다.

 

1. 시프트 연산자(Shift Operator)?

 

이번에 알아볼 연산자의 이름은 바로 시프트 연산자(Shift Operator)이다.

시프트... 시프트가 뭐지?

우리가 지금도 사용하고 있는 키보드에 양 옆으로 길게 붙어있는 시프트키.

우리가 영어 대소문자를 쓰거나 특수기호를 쓸 때 함께 누르는 키인데

시프트는 사전적 의미로 이동하다, 옮기다라는 뜻을 가지고 있다.

즉, 프로그래밍에서 말하는 시프트는 의미 그대로 이동시키는 것을 말한다.

그렇다면 도대체 뭘 이동시키는 것일까?

그것을 알아보기 전에 일단 시프트 연산자의 형태를 알아보자.

 

2. <<, >>

시프트 연산자에는 << >>가 있는데 이는 무슨 뜻인지는 몰라도

방향을 가리키는 모습처럼 보이기도 하다.

그래서 <<는 왠지 모르게 왼쪽으로 이동시킬거 같고

>>는 오른쪽으로 이동시킬거 같은 느낌이 다분히 든다.

시프트 연산자에는 <<와 >> 말고도 3개가 붙은 >>>도 있지만

여기에서는 2개가 붙어있는 <<와 >>만 알아보도록 하자.

(필요한 것만 배우자.)

 

앞서 추측한 내용이 90%정도는 맞다고 생각하면 된다.

그렇다면 남은 10%에 대해서 알아봐야 할텐데

여기에서 등장하는 것이 바로 이전에 알아봤던 비트전환연산자(~)에서 사용했던

10진수를 2진수로 표현하는 것이다.

 

결국 시프트 연산자 2진수, 다시 말해, 비트를 이동시키는 연산자라는 뜻이다.

 

그렇다면 이제 본격적으로 시프트 연산자가 어떻게 동작하는지 알아보자.

 

3. 시프트 연산

 

앞서 언급했듯이 시프트 연산자 비트를 이동시키는 연산자가 되겠다.

그럼 바로 예시를 들어보자.

우리는 1byte, 즉, 8bit를 기준으로 생각하고 비트를 표현할 것이다.

10진수의 정수 10이 있다면 이를 2진수로 변환하면 다음과 같다.

0 0 0 0 1 0 1 0

여기에 시프트 연산자를 사용하면 이렇게 표현할 수 있다.

 

10 << 2

 

시프트 연산자 피연산자가 2개 2항 연산자인데

하나씩 의미를 파악해보자.

먼저 앞에 붙은 10은 10진수의 정수 10을 말하는 것이고

<<는 왼쪽으로 시프트를 하라는 연산자이다.

그리고 마지막에 있는 2는 2칸을 이동하라는 뜻이 된다.

 

종합하면 10진수의 정수 10을 2진수로 변환한 비트 값을 왼쪽으로 2칸씩 이동하라는 뜻이 되겠다.

그렇다면 이 연산자를 실행해보자.

그러면 앞서 2진수로 변환한 10은 다음과 같이 변하는 것을 알 수 있다.

0 0 1 0 1 0 0 0

이 2진수를 다시 10진수로 변환해보자.

그러면 40이 되는 것을 알 수 있는데

여기에서 시프트 연산자의 계산 공식을 알 수 있게 된다.

 

10에서 40이 되는 걸 살펴보면

10 * 4라는 것을 알 수 있고 4는 2의 제곱이라는 것도 유추할 수가 있다.

따라서 10 << 2는 10 * 2의 2제곱이라는 것을 알 수 있다.

즉 x << n은 x * 2^n이라는 공식이 성립하게 되는 것이다.

하지만 이 공식을 외운다기 보다는 비트가 이동하는 것을 외알고 있는 것을 추천,

아니 이 것만 기억하기를 바란다.

우리는 연산자가 어떻게 동작하는지를 배우는 것이지

단순히 숫자계산을 하기 위해, 시험 문제를 풀기 위해 배우는게 절대 아니란 걸 인지하길 바란다.

 

그렇다면 >>는 어떻게 될까?

다시 10진수의 정수 10을 2진수로 소환하겠다.

0 0 0 0 1 0 1 0

이제는 시프트 연산자 >>를 실행해보겠다.

 

10 >> 2

 

를 실행하면 다음과 같이 변하게 된다.

0 0 0 0 0 0 1 0

비트 전체를 오른쪽으로 2칸을 이동시키는 동작을 하게 된다.

그런데 여기에서 문제가 발생하게 된다.

자세히 보면 비트 범위 밖으로 1이 넘어가 버리면서 사라지게 된 것이다.

이건 어떻게 되는 것일까?

 

정답은 그냥 사라진다.

시프트 연산자는 값이 허용범위를 넘어가버리면 그냥 없는 값이 되어버린다.

소수점이라는 개념이 없기 때문에 그냥 없는 값이 되어버린다.

 

만약 저기에서

 

10 >> 2

 

가 아닌

 

10 >> 4

 

가 되었다면

0 0 0 0 0 0 0 0

비트 전체를 오른쪽으로 4칸을 이동했기 때문에 1이 모두 사라지게 되고

결과는 위와 같이 0만이 남게 되는 것이다.

즉, 데이터 손실이 발생하게 된다.

우리가 어디에서 어떻게 시프트 연산자라는 녀석을 만나게 될지는 모르겠지만

이러한 특징도 가지고 있다는 것을 알아두면 좋겠다.

 

4. 마무리

 

이번 시간에는 시프트 연산자(Operator)에 대해서 알아봤다.

시프트 연산자 이동시키는 연산자인데 무엇을 이동시키냐면

2진수로 표현된 비트를 해당하는 방향으로 이동시키는 연산자가 되겠다.

10 >> 2라면

10진수의 정수 10을 2진수로 변환한 값을 오른쪽으로 2칸 이동한 것이고

20 << 4라면

10진수의 정수 20을 2진수로 변환한 값을 왼쪽으로 4칸 이동한 것이다.

Comments