비트 연산

_ dfdeer·2025년 7월 14일

시프트 연산

비트는 시프트 연산을 통해 이동시켜 값을 바꿀 수 있다.

예를 들어 int a = 6 라고 선언 했을때, 6은 10진수이므로 비트로 표현하기 위해서는 2진법을 통해 표현해야한다.
-> 0000 0110 (6)

여기서 시프트 연산을 통해 값을 바꾸는 방법은 '<<' 혹은 '>>' 기호를 사용하면 된다.
a << 2 라고 표현을 하면 왼쪽으로 비트들이 2칸 이동한 것이다.
-> 0001 1000 (24)

또한 이 연산들은 2의 n승으로 쉽게 값을 알아낼 수 있다.
a << 3 -> 6 x 2^3(8) 이므로 0011 0000(24)이다.
a >> 1 -> 6 / 2^1(2) 이므로 0000 0011(3)이다.

비트마스크

비트들의 집합을 구현할 수 있는 게 비트마스크라고 한다.
근데 아직까진 정확히 뭔지 잘 모르겠다.

대충 반복문을 이용해 부분 집합들을 확인하는 것까지는 알겠는데 정확히 무슨 역할을 하는지, 어떤 곳에 사용하는지를 잘 모르겠다.

개념 자체를 제대로 이해하지 못하고 있어서인지, 비트마스크를 설명하라하면 막막하게 느껴진다.

시프트 연산의 원리

왼쪽 시프트 연산자 '<<' 를 사용하게 되면 오른쪽에 생긴 빈 자리에는 항상 0이 채워지고, 오른쪽 시프트 연산자인 '>>'를 사용하게 되면 왼쪽에 생긴 빈자리에는 0 혹은 1이 채워진다.
부호가 없으면 0, 있으면 1이 채워진다.

이런 이유는 만약 변수를 unsigned 로 선언했을 시, 부호 비트가 없으므로 논리 시프트 연산이 되므로 빈 자리에는 항상 0이 채워진다. 하지만 변수를 signed 로 선언하면 부호 비트가 존재하므로 빈 자리가 생길 시 최상위 비트를 채우는 산술 시프트 연산이 된다. 이는 보수법을 적용했기 때문이다.

만약 0000 1101(13) 이라는 수를 음수로 바꾸려면 최상위 비트를 1로 바꾸어 1000 1101(-13)로 부호 절대값 방식으로 표현할 수도 있지만, 연산을 위해서는 2의 보수를 적용한다.
그리고 1의 보수를 적용하지 않는 이유로는 2의 보수는 0이 그저 0 하나만 존재하지만, 1의 보수에서는 +0과 -0이 존재할 수 있기 때문이다.

0000 0000(+0) / 1000 0000(-0)

2의 보수는 1의 보수(0은 1, 1은 0으로)를 적용 후 제일 오른쪽 비트에 +1을 하는 방식이다.
따라서 0000 1101 > 1111 0010 > 1111 0011 이렇게 되는 것이다.

0개의 댓글