memoryview에 대한 문서 확인 :
memoryview 객체를 사용하면 Python 코드가 복사없이 버퍼 프로토콜을 지원하는 객체의 내부 데이터에 액세스 할 수 있습니다.
클래스 memoryview (obj)
obj를 참조하는 memoryview를 만듭니다. obj는 버퍼 프로토콜을 지원해야합니다. 버퍼 프로토콜을 지원하는 기본 제공 개체에는 바이트 및 바이트 배열이 포함됩니다.
그런 다음 샘플 코드가 제공됩니다.
>>> v = memoryview(b'abcefg')
>>> v[1]
98
>>> v[-1]
103
>>> v[1:4]
<memory at 0x7f3ddc9f4350>
>>> bytes(v[1:4])
b'bce'
인용문은 이제 자세히 살펴 보겠습니다.
>>> b = b'long bytes stream'
>>> b.startswith(b'long')
True
>>> v = memoryview(b)
>>> vsub = v[5:]
>>> vsub.startswith(b'bytes')
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
AttributeError: 'memoryview' object has no attribute 'startswith'
>>> bytes(vsub).startswith(b'bytes')
True
>>>
그래서 내가 위에서 모은 것은 :
복사하지 않고 버퍼 객체의 내부 데이터를 노출하는 memoryview 객체를 생성합니다. 그러나 객체에 대해 유용한 작업을 수행하려면 (객체가 제공하는 메소드를 호출하여) 사본을 생성해야합니다!
일반적으로 메모리 뷰 (또는 이전 버퍼 객체)는 큰 객체가있을 때 필요하며 슬라이스도 클 수 있습니다. 큰 조각을 만들거나 작은 조각을 여러 번 만들면 더 나은 효율성이 필요합니다.
위의 계획을 사용하면 누군가 내가 여기서 놓친 것을 설명 할 수 없다면 어떤 상황에서도 유용 할 수 있는지 알 수 없습니다.
편집 1 :
우리는 많은 양의 데이터를 가지고 있으며, 예를 들어 버퍼가 소모 될 때까지 문자열 버퍼의 시작 부분에서 토큰을 추출하는 것과 같이 처음부터 끝까지 진행하여 처리하려고합니다 .C 용어에서 이것은 포인터를 통해 포인터를 이동하는 것입니다. 버퍼 및 포인터는 버퍼 유형을 예상하는 모든 함수에 전달할 수 있습니다. 파이썬에서 비슷한 일을 어떻게 할 수 있습니까?
사람들은 해결 방법을 제안합니다. 예를 들어 많은 문자열 및 정규식 함수가 포인터 전진을 에뮬레이트하는 데 사용할 수있는 위치 인수를 사용합니다. 여기에는 두 가지 문제가 있습니다. 첫 번째는 해결 방법이고, 단점을 극복하기 위해 코딩 스타일을 변경해야합니다. 두 번째 : 모든 함수에 위치 인수가있는 것은 아닙니다 (예 : regex 함수 및 startswith
수행 encode()
/ decode()
하지 않음).
다른 사람들은 데이터를 청크로로드하거나 최대 토큰보다 큰 작은 세그먼트로 버퍼를 처리하도록 제안 할 수 있습니다. 좋아, 우리는 이러한 가능한 해결 방법을 알고 있지만, 코딩 스타일을 언어에 맞게 구부리지 않고 파이썬에서 더 자연스러운 방식으로 작업해야합니다. 그렇지 않습니까?
편집 2 :
코드 샘플은 일을 더 명확하게합니다. 이것이 제가하고 싶은 일이고, memoryview가 언뜻보기에 할 수있는 일이라고 생각했습니다. 내가 찾고있는 기능에 대해 pmview (적절한 메모리보기)를 사용할 수 있습니다.
tokens = []
xlarge_str = get_string()
xlarge_str_view = pmview(xlarge_str)
while True:
token = get_token(xlarge_str_view)
if token:
xlarge_str_view = xlarge_str_view.vslice(len(token))
# vslice: view slice: default stop paramter at end of buffer
tokens.append(token)
else:
break