이 질문의 역사
리스트(list)는 파이썬의 기본 내장 데이터 유형 중 하나로, 언어의 초기 버전부터 존재했습니다. 시간이 지남에 따라 내부 구조가 개선되어 성능과 프로그래밍 편의성이 향상되었습니다.
문제
중요한 점은 파이썬의 리스트가 연결 리스트로 구현되지 않고 동적 배열로 구현된다는 것입니다. 잘못된 이해는 비효율적인 코드 또는 연산의 복잡도를 잘못 계산하는 결과를 초래할 수 있습니다.
해결책
리스트는 필요할 때 메모리 크기를 "점프"하여 늘리는 동적 배열로 구현되어 있어, 요소를 추가할 때 발생하는 지속적인 비용을 피할 수 있습니다. 이를 통해 리스트 끝에 요소를 삽입하거나 삭제하는 작업이 평균 O(1) 시간이 걸립니다. 중간이나 처음에 삽입하거나 삭제하는 작업은 요소 이동이 필요하기 때문에 O(n) 시간이 소요됩니다.
코드 예제:
my_list = [1, 2, 3] my_list.append(4) # 끝에 추가하기 my_list.insert(1, 'a') # 인덱스에 삽입하기 print(my_list)
주요 특징:
파이썬의 리스트를 C의 배열과 같다고 볼 수 있을까요? 그 차이는 무엇인가요?
아니요, C의 배열은 고정된 타입의 요소들이 메모리에 연속적으로 저장됩니다. 파이썬 리스트는 객체에 대한 포인터 배열로, 각각의 포인터는 힙에 있는 자율적인 임의 타입 객체를 참조합니다.
루프에서 리스트의 시작 부분에 요소를 삽입하면 어떻게 되나요? 빠른가요?
아니요, 느립니다: 매번 (위치 0에) 요소를 삽입할 때마다 모든 기존 요소가 오른쪽으로 이동해야 합니다. 평균 복잡도는 O(n)이며, 큰 리스트의 경우 성능 저하를 초래합니다.
리스트를 위한 + 연산자와 append/extend의 차이는 무엇인가요?
lst1 = [1, 2] lst2 = [3, 4] lst3 = lst1 + lst2 # lst3는 새로운 리스트 lst1.append(lst2) # lst1은 [1, 2, [3, 4]]가 됨 lst1.extend(lst2) # lst1은 [1, 2, 3, 4]가 됨, lst1이 이전 append 이후 리셋되지 않았을 경우
프로젝트에서 첫 요소를 저장하고 지속적으로 삭제하는 데 리스트가 사용되었습니다. 데이터 양이 많을 때 현저한 속도 저하가 발생했습니다.
장점:
단점:
문제를 파악한 후, 리스트를 collections.deque로 교체하여 이러한 작업에 최적화되었습니다.
장점:
단점: