일반적인 느낌은 Python 자체는 바이너리를 지원하지 않지만 이를 보완하기 위한 모듈, 즉 struct 모듈을 제공한다는 것입니다.
구조체 가져오기a=12.34#a를 바이너리로 변환 bytes=struct.pack('i',a)이때 bytes는 문자열 문자열이고, 그 문자열은 바이트 단위의 바이너리 저장 내용과 동일합니다. 그런 다음 기존 바이너리 데이터 바이트(실제로는 문자열)를 역연산하여 Python 데이터 유형으로 다시 변환합니다. a,=struct .unpack ('i',bytes)unpack은 tuple을 반환하므로 변수가 하나만 있는 경우: bytes=struct.pack('i' ,a ) 그런 다음 디코딩할 때 다음을 수행해야 합니다. a,=struct.unpack('i',bytes) 또는 (a,)=struct.unpack('i', bytes )a=struct.unpack('i',bytes)를 직접 사용하면 a=(12.34,)는 원래 부동 소수점 숫자 대신 튜플입니다. 여러개의 데이터로 구성된다면 다음과 같을 수 있습니다.
a='hello' b='world!' c=2 d=45.123 bytes=struct.pack('5s6sif',a,b,c,d)이때 바이트는 바이너리 형태의 데이터이고, binfile.write(bytes)와 같은 파일을 직접 작성한 다음 필요할 때 읽어서 bytes=binfile.read() 파이썬으로 디코딩합니다. struct.unpack() 변수를 통해a,b,c,d=struct.unpack('5s6sif',bytes)'5s6sif'는 형식 문자열인 fmt라고 하며, 숫자와 문자로 구성됩니다. 5s는 5자의 문자열을 나타내고, 2i는 2개의 정수를 나타냅니다. 다음은 Python에서 사용 가능한 문자와 유형입니다.
형식 | C 유형 | Python | 바이트 수 |
---|---|---|---|
x | 패드 바이트 | 값 없음 | 1 |
c | char | 길이 1의 문자열 | 1 |
b | 부호 있는 문자 | 정수 | 1 |
B | 부호 없는 문자 | 정수 | 1 |
? | _Bool | bool | 1 |
h | 짧음 | 정수 | 2 |
H | 부호 없는 짧음 | 정수 | 2 |
i | 정수 | 정수 | 4 |
I | unsigned int | 정수 또는 long | 4 | tr>
l | 긴 | 정수 | 4 |
L td> | 부호 없는 긴 | 긴 | 4 |
q | 긴 긴 | 긴 | 8 |
Q | 부호 없는 긴 긴 | 긴 | 8 |
f | 부동 | 부동 | 4 |
d | 더블 | 플로트 | 8 |
s | char[] | string | 1 |
p | char[] td> | 문자열 | 1 |
P | void * | long |
Format | C Type | Python | 字节数 |
---|---|---|---|
x | pad byte | no value | 1 |
c | char | string of length 1 | 1 |
b | signed char | integer | 1 |
B | unsigned char | integer | 1 |
? | _Bool | bool | 1 |
h | short | integer | 2 |
H | unsigned short | integer | 2 |
i | int | integer | 4 |
I | unsigned int | integer or long | 4 |
l | long | integer | 4 |
L | unsigned long | long | 4 |
q | long long | long | 8 |
Q | unsigned long long | long | 8 |
f | float | float | 4 |
d | double | float | 8 |
s | char[] | string | 1 |
p | char[] | string | 1 |
P | void * | long |
사용방법은 '@5s6sif'처럼 fmt의 첫 번째 위치에 놓는 것입니다
------바이너리 파일 처리 시 발생하는 문제--- --
바이너리 파일을 처리할 때 바이너리 파일을 읽으려면
binfile=open(filepath,'rb')
또는
binfile=open(filepath,'wb') 바이너리 파일 쓰기그럼 binfile=open(filepath,'r') 결과의 차이점은 무엇인가요? 두 가지 차이점이 있습니다. 먼저 'r' 사용시 '0x1A'를 만나면 파일의 끝, 즉 EOF로 간주됩니다. 'rb'를 사용하면 이 문제가 발생하지 않습니다. 즉, 바이너리로 쓰고 텍스트로 읽는 경우 '0X1A'가 있으면 파일의 일부만 읽혀지게 됩니다. 'rb'를 사용하면 파일 끝까지 읽습니다. 둘째, 문자열 x='abc/ndef'에 대해 len(x)를 사용하여 길이를 7로 만들 수 있습니다. /n은 개행 문자라고 하며 실제로는 '0X0A'입니다. 텍스트 모드인 'w'로 쓰면, 윈도우 플랫폼에서는 '0X0A'가 자동으로 '0X0D', '0X0A'라는 두 글자로 바뀌게 되는데, 즉 실제로 파일 길이가 8이 된다. 'r' 텍스트 모드로 읽으면 자동으로 원래 개행 문자로 변환됩니다. 쓰기 위해 'wb' 바이너리 모드로 변경하면 한 문자는 그대로 유지되며, 읽을 때 그대로 읽혀지게 됩니다. 따라서 텍스트 모드로 쓰고 바이너리 모드로 읽는 경우 이 추가 바이트를 고려해야 합니다. '0X0D'는 캐리지 리턴 문자라고도 합니다.Linux에서는 변경되지 않습니다. 리눅스는 줄바꿈을 표현하기 위해 '0X0A'만을 사용하기 때문입니다.