문자열을 사용하여 압축하고 문자열 zlib
로 텍스트 메시지에 추가하고 싶습니다 . 몇 가지 문제가 있습니다.
ㅏ. "이진"문자열과 일반 문자열을 결합하는 데 문제가 있습니까? 예를 들어, 소켓을 통해 다음과 같은 문자열을 보내는 데 문제가 있습니까?
MSG 10=12 20=x\x9c+(\xc0\x00\x00S3\x08Q 33=hansz
나는 파일을 열 때 보통 그가 바이너리 모드에서 읽을 것인지 아닌지를 선언하기 때문에 그것을 묻고 나는 그것을 완전히 이해하지 못했습니다.
비. 압축 된 문자열에 일부 문자가 나타나지 않는지 확인할 수 있습니까? 예를 들어 압축 된 문자열에와 같은 문자 시퀀스가 포함 x\x9c 33=eve
되면 메시지를 제대로 구문 분석하는 데 문제가 있습니다. 공백이 zlib
압축 된 문자열에 표시되지 않는다는 것을 알고 있으면 문자열 분할을 수행 할 수 있습니다. 따옴표와 아포스트로피가 나타나지 않는 것을 알고 있다면 shlex
split을 사용할 수 있습니다 .
씨. 내 의도 중 하나를 사용하는 것 zlib.compress(str(obj))
또는 zlib.compress(pickle.dumps(obj))
산세의 종류 및 사용 중 하나로 eval(zlib.decompress(s))
또는 pickle.loads(zlib.decompress(s))
unpickling을 위해. 이해가 되나요? 첫 번째 아이디어는 덜 안전 eval
하지만 (그렇게 안전하지는 않지만) 내부 시스템이므로 괜찮습니다. 반면에 압축은 대부분의 경우 더 짧고 빠릅니다. 좋은 습관이라고 생각하세요?
디. 이 메시지를 짧게 만들고 싶은 이유는 나중에 소켓을 통해 보내고 싶기 때문입니다. 나는 소켓에 능숙하지 않지만 이것이 작은 (4k?) 버퍼를 읽는 경향이 있다는 것을 알고 있으므로 메시지를 그보다 길지 않게 만들려고합니다.
ㅏ. 바이트와 유니 코드 문자열을 결합 할 때 발생하는 문제는 다음과 같습니다. 255 개 이상의 문자가 있습니다. 따라서 역사적으로 수백 개의 인코딩이 만들어져 서로 다른 알파벳을 1 바이트에 넣었습니다.
>>> print b'\xE4'.decode('cp1251') # russian d
д
>>> print b'\xE4'.decode('cp1252') # german ae
ä
글자는 다른 의미를 가지고 있습니다. 이러한 문자의 의미를 잃지 않으려면 유니 코드를 사용합니다.
>>> print u'\u00e4\u0434'
äд
그러나 바이트가 표시되면 인코딩을 모를 수 있습니다. 따라서 한 바이트가 다른 문자 일 수 있으므로 유니 코드와 바이트를 바로 결합 할 수 없습니다.
'UTF-8'
향후 몇 년 동안 인코딩으로 사용하십시오 . 필요한 경우 1 바이트 이상을 사용하고 모든 문자를 저장합니다.
비. zlib는 바이트를 취하고 바이트를 출력합니다. 모든 바이트를 포함 할 수 있습니다.
씨. zlib.compress(pickle.dumps(obj))
그리고 pickle.loads(zlib.decompress(s))
완전히 괜찮습니다. Pickle은 객체를 취하고 바이트를 반환합니다. 저장하고보다 더 많은 개체에 저장할 수 있습니다 zlib.compress(repr(obj))
와 eval(zlib.decompress(s))
. pickle
만큼 안전합니다 eval
. 저장 평가가 필요한 경우을 import ast
ast.literal_eval
보거나 json
대신 사용하십시오 pickle
.
디. 메시지가 언제 끝나고 다른 메시지가 시작되는지 확인하십시오. 이것을 zlib.decompressobj
위해 사용할 수 있다고 생각합니다 . 그렇지 않으면 zib가 혼동 될 수 있습니다. 소켓은 4k 바이트 이상을 보낼 수 있습니다. 버퍼는 소켓이 최대 4k 바이트를 저장하고 버퍼에서 바이트를 가져올 때까지 더 이상 수신하지 않음을 의미합니다. TCP를 사용하면 끝없는 바이트 스트림을 보낼 수 있으며 손실되는 것은 없습니다.
이 기사는 인터넷에서 수집됩니다. 재 인쇄 할 때 출처를 알려주십시오.
침해가 발생한 경우 연락 주시기 바랍니다[email protected] 삭제
몇 마디 만하겠습니다