Python 비트 연산자(논리 곱, 논리 OR, 배타적 OR, 반전, 시프트)

사업

Python은 이진 정수 유형 int 값의 각 비트에 대해 논리 결합, 논리 분리, 배타적 분리, 비트 반전, 왼쪽 비트 시프트 및 오른쪽 비트 시프트를 각각 수행하는 다음 비트 연산자를 제공합니다.

  • &
  • |
  • ^
  • ~
  • <<
  • >>

이 섹션에서는 먼저 다음을 설명합니다.

  • 교차로(AND) :&
  • 분리(OR) :|
  • EXCLUSIVE-OR 연산(XOR) :^

다음으로 우리는 다음을 논의할 것입니다.

  • 음수에 대한 비트 연산
  • 비트 플립( NOT) :~
  • 비트 시프트:<<,>>

2진수, 8진수, 16진수로 정수를 쓰는 방법과 다음 함수를 사용하여 2진수, 8진수, 16진수 숫자와 문자열을 변환하는 방법에 대한 자세한 내용은 다음 문서를 참조하세요.

  • bin()
  • oct()
  • hex()
  • format()

또한, 비트 연산이 아닌 부울 값(true, false)에 대한 논리 연산(부울 연산)에 대해서는 다음 문서를 참조하십시오. &,| 대신 and,or를 사용합니다.

교차로(AND) :&운영자

이것은 & 연산자, 결과는 bin()에 의해 이진 표기법의 문자열로 변환됩니다.

x = 9   # 0b1001
y = 10  # 0b1010

print(x & y)
print(bin(x & y))
# 8
# 0b1000

분리(OR) :|운영자

|를 사용하는 논리 곱(OR)의 예 연산자, 결과는 bin()에 의해 이진 표기법의 문자열로 변환되고 함께 출력됩니다.

print(x | y)
print(bin(x | y))
# 11
# 0b1011

EXCLUSIVE-OR 연산(XOR) :^운영자

bin()을 사용하여 이진 표기법의 문자열로 변환한 결과와 결합된 ^ 연산자를 사용하는 논리곱(XOR)의 예.

print(x ^ y)
print(bin(x ^ y))
# 3
# 0b11

논리 AND, OR, XOR의 각 비트에 대한 입력과 출력의 관계는 아래 표와 같습니다.

입력 1입력 2교차로(AND)분리(OR)EXCLUSIVE-OR 연산(XOR)
11110
10011
01011
00000

음수에 대한 비트 연산

음의 정수에 대해 비트 연산을 수행할 때 값은 2의 보수 형식으로 표현된 것처럼 처리됩니다.

그러나 bin() 또는 format()을 사용하여 음의 정수를 이진 문자열로 변환하는 경우 절대값은 2의 보수 형식 대신 빼기 기호를 갖습니다.

2의 보수 표현으로 문자열을 얻으려면 아래와 같이 필요한 최대 비트 자릿수와 함께 AND를 취하십시오.

  • 4비트용0b1111(=0xf)
  • 8비트용0xff
  • 16비트용0xffff

2의 보수 표현 문자열을 얻을 수 있습니다(각 비트가 반전되고 1이 추가됨).

x = -9

print(x)
print(bin(x))
# -9
# -0b1001

print(bin(x & 0xff))
print(format(x & 0xffff, 'x'))
# 0b11110111
# fff7

비트 플립:~운영자

~ 연산자로 비트 뒤집기의 예.

비트 단위 반전은 단순히 반전된 각 비트의 값이 아닙니다. 이 연산자를 사용할 때 반환 값은 다음과 같습니다.
~x#ERROR!-(x+1)

-(x+1)이 값은 입력 값 x를 2의 보수 형식으로 간주하고 모든 비트를 반전하는 것과 같습니다.

앞서 언급한 바와 같이 파이썬에서는 bin(), format() 등을 이용하여 음의 정수를 이진 문자열로 변환할 때 2의 보수 형태가 아니라 빼기 부호가 붙은 절대값이다. 따라서 ~x를 문자열로 직접 변환하면 원래 값의 비트가 반전된 문자열이 생성되지 않습니다.

x = 9  # 0b1001

print(~x)
print(bin(~x))
# -10
# -0b1010

AND 연산을 수행하여 2의 보수 표현의 문자열로 바꾸면 원래 값의 비트가 반전되는 것을 볼 수 있습니다.

또한, 예를 들어 있는 그대로 반전된 4자리 비트 문자열인 비트 문자열을 얻으려면(부호 비트 생략) format()을 사용하여 다음과 같이 AND된 값에 대해 0을 채우십시오.04b'

print(bin(~x & 0xff))
print(format(~x & 0b1111, '04b'))
# 0b11110110
# 0110

비트 시프트:<<,>>

비트 시프트 연산자를 사용한 왼쪽 비트 시프트 및 오른쪽 비트 시프트의 예.

x = 9  # 0b1001

print(x << 1)
print(bin(x << 1))
# 18
# 0b10010

print(x >> 1)
print(bin(x >> 1))
# 4
# 0b100

음수 값의 경우 부호 비트가 확장 및 이동되고 양수/음수 부호는 동일하게 유지됩니다. 음수 값은 왼쪽 끝까지 1의 선 이미지입니다.

x = -9
print(bin(x))
print(bin(x & 0xff))
# -0b1001
# 0b11110111

print(x << 1)
print(bin(x << 1))
print(bin((x << 1) & 0xff))
# -18
# -0b10010
# 0b11101110

print(x >> 1)
print(bin(x >> 1))
print(bin((x >> 1) & 0xff))
# -5
# -0b101
# 0b11111011

숫자로 생각하는 것은 명확하지 않기 때문에 2의 보수 표현식의 문자열로 생각하는 것이 좋습니다.