Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> Python

Container Datatypes ใน Python (โมดูล collections)

โมดูล collections ให้ Container Datatypes ที่ทรงพลังกว่า Built-ins (dict, list, set, tuple)


Container Types ภาพรวม

Classคำอธิบายใช้เมื่อไหร่
namedtupleTuple ที่มีชื่อ FieldImmutable Record, Lightweight Object
dequeDouble-Ended Queue O(1)Queue, Stack, Sliding Window, BFS
CounterDict Subclass นับ Hashable ObjectsFrequency Counting, Multiset
OrderedDictDict จดจำ Insertion OrderLRU Cache, Ordered Config
ChainMapรวมหลาย Dict เป็น View เดียวConfig Layers, Scope Chain
defaultdictDict ที่มี Default FactoryGrouping, Counting, Nested Dict
UserDict/UserList/UserStringWrapper สำหรับ SubclassingCustom Dict/List Behavior

Deque (Double-Ended Queue)

from collections import deque

dq = deque('124dfre')
dq.append('x')        # Right
dq.appendleft('B')    # Left
dq.pop()              # Right
dq.popleft()          # Left
dq.rotate(3)          # Rotate Right 3
dq.reverse()          # Reverse In-place

Methods: append, appendleft, pop, popleft, extend, extendleft, rotate, reverse, index, count, insert, remove, clear


Counter

from collections import Counter

cnt = Counter(['ABC', 'PQR', 'ABC', 'ABC', 'PQR', 'Mno', 'xyz', 'PQR', 'ABC', 'xyz'])
print(cnt)                    # Counter({'ABC': 4, 'PQR': 3, 'xyz': 2, 'Mno': 1})
print(cnt.most_common(2))     # [('ABC', 4), ('PQR', 3)]
print(list(cnt.elements()))   # ['ABC', 'ABC', 'ABC', 'ABC', 'PQR', ...]

# Arithmetic
c1 = Counter(a=3, b=1)
c2 = Counter(a=1, b=2)
print(c1 + c2)   # Counter({'a': 4, 'b': 3})
print(c1 - c2)   # Counter({'a': 2})  (เฉพาะ Positive)
print(c1 & c2)   # Intersection (Min)
print(c1 | c2)   # Union (Max)

ChainMap

from collections import ChainMap

defaults = {'host': 'localhost', 'port': 8080}
user_config = {'port': 3000}
env_config = {'host': '0.0.0.0'}

config = ChainMap(env_config, user_config, defaults)
print(config['host'])  # '0.0.0.0'
print(config['port'])  # 3000

config = config.new_child({'debug': True})  # Add Layer

OrderedDict

from collections import OrderedDict

od = OrderedDict()
od['a'] = 1
od['b'] = 2
od.move_to_end('a')     # Move to End
od.move_to_end('b', last=False)  # Move to Front
od.popitem(last=False)  # Pop Front (FIFO)

defaultdict

from collections import defaultdict

# Grouping
words = ['apple', 'bat', 'bar', 'atom', 'book']
groups = defaultdict(list)
for w in words:
    groups[w[0]].append(w)
# {'a': ['apple', 'atom'], 'b': ['bat', 'bar', 'book']}

# Nested Defaultdict
tree = lambda: defaultdict(tree)
data = tree()
data['a']['b']['c'] = 1

UserDict / UserList / UserString

from collections import UserDict

class ValidatedDict(UserDict):
    def __setitem__(self, key, value):
        if not isinstance(key, str):
            raise TypeError("Keys must be strings")
        super().__setitem__(key, value)

vd = ValidatedDict()
vd['name'] = 'John'  # OK
# vd[123] = 'Error'  # TypeError

สรุปเลือกใช้

  • ต้องการ Queue/Stack -> deque
  • นับ Frequency -> Counter
  • Config Layers -> ChainMap
  • Dict ที่ต้องการ Order -> OrderedDict (หรือ dict ใน 3.7+)
  • Dict ที่ Auto-create Default -> defaultdict
  • Custom Container Behavior -> UserDict/UserList