Collection Classes

Specialized collection classes with enhanced functionality beyond Python’s built-in collections.

attrdict

Six dictionary classes with special behaviors:

  • attrdict: Attribute-style access (dot notation)

  • lazydict: Lazy evaluation of function values

  • emptydict: Returns None for missing keys

  • bidict: Bidirectional dictionary with inverse mapping

  • MutableDict: Ordered dict with insert_before/insert_after

  • CaseInsensitiveDict: Case-insensitive key access

class attrdict[source]

Bases: dict

A dictionary subclass that allows attribute-style access.

This is a dictionary that allows access to its keys as attributes (using dot notation) in addition to standard dictionary access methods.

Basic Usage:

>>> import copy
>>> d = attrdict(x=10, y='foo')
>>> d.x
10
>>> d['x']
10
>>> d.y = 'baa'
>>> d['y']
'baa'
>>> g = d.copy()
>>> g.x = 11
>>> d.x
10
>>> d.z = 1
>>> d.z
1
>>> 'x' in d
True
>>> 'w' in d
False
>>> d.get('x')
10
>>> d.get('w')

Deep Copy Behavior:

>>> tricky = [d, g]
>>> tricky2 = copy.copy(tricky)
>>> tricky2[1].x
11
>>> tricky2[1].x = 12
>>> tricky[1].x
12
>>> righty = copy.deepcopy(tricky)
>>> righty[1].x
12
>>> righty[1].x = 13
>>> tricky[1].x
12

Access Methods (handles obj.get('attr'), obj['attr'], and obj.attr):

>>> class A(attrdict):
...     @property
...     def x(self):
...         return 1
>>> a = A()
>>> a['x'] == a.x == a.get('x')
True
>>> a.get('b')
>>> a['b']
Traceback (most recent call last):
    ...
KeyError: 'b'
>>> a.b
Traceback (most recent call last):
    ...
AttributeError: b
get(key, default=None)[source]
update(*args, **kwargs)[source]
copy(**kwargs)[source]
class lazydict[source]

Bases: attrdict

A dictionary where function values are lazily evaluated.

Functions stored as values are called with the dictionary as argument when the key is accessed, making them behave like computed properties.

Basic Usage:

>>> a = lazydict(a=1, b=2, c=lambda x: x.a+x.b)
>>> a.c
3
>>> a.a = 99
>>> a.c  # Recalculated with new value
101
>>> a.z = 1
>>> a.z
1

Instance Isolation (descriptors are not shared between instances):

>>> z = lazydict(a=2, y=4, f=lambda x: x.a*x.y)
>>> z.b
Traceback (most recent call last):
    ...
AttributeError: b
>>> z.c
Traceback (most recent call last):
    ...
AttributeError: c
>>> z.f
8
>>> a.f
Traceback (most recent call last):
    ...
AttributeError: f
class emptydict[source]

Bases: attrdict

A dictionary that returns None for non-existing keys without raising exceptions.

Similar to attrdict but returns None instead of raising KeyError or AttributeError when accessing non-existing keys.

Basic Usage:

>>> a = emptydict(a=1, b=2)
>>> a.c == None
True
>>> a.b
2
>>> a['b']
2
>>> 'c' in a
False
>>> 'b' in a
True
>>> a.get('b')
2
>>> a.get('c')
class bidict(*args, **kwargs)[source]

Bases: dict

Bidirectional dictionary that allows multiple keys with the same value.

Maintains an inverse mapping from values to lists of keys that enables bidirectional lookup.

Basic Usage:

>>> bd = bidict({'a': 1, 'b': 2})
>>> bd
{'a': 1, 'b': 2}
>>> bd.inverse
{1: ['a'], 2: ['b']}

Multiple Keys with Same Value:

>>> bd['c'] = 1
>>> bd
{'a': 1, 'b': 2, 'c': 1}
>>> bd.inverse
{1: ['a', 'c'], 2: ['b']}

Removing Keys Updates Inverse:

>>> del bd['c']
>>> bd
{'a': 1, 'b': 2}
>>> bd.inverse
{1: ['a'], 2: ['b']}
>>> del bd['a']
>>> bd
{'b': 2}
>>> bd.inverse
{2: ['b']}

Changing Values Updates Inverse:

>>> bd['b'] = 3
>>> bd
{'b': 3}
>>> bd.inverse
{2: [], 3: ['b']}
inverse
class MutableDict[source]

Bases: dict

An ordered dictionary with additional insertion methods.

Extends the standard dictionary with methods to insert items before or after existing keys. Relies on Python 3.7+ dictionary implementation which preserves insertion order.

insert_before(key, new_key, val)[source]

Insert new_key:value into dict before key.

Example:

>>> d = MutableDict({'a': 1, 'b': 2, 'c': 3})
>>> d.insert_before('b', 'x', 10)
>>> list(d.keys())
['a', 'x', 'b', 'c']
>>> d['x']
10
insert_after(key, new_key, val)[source]

Insert new_key:value into dict after key.

Example:

>>> d = MutableDict({'a': 1, 'b': 2, 'c': 3})
>>> d.insert_after('a', 'x', 10)
>>> list(d.keys())
['a', 'x', 'b', 'c']
>>> d['x']
10
class CaseInsensitiveDict(data=None, **kwargs)[source]

Bases: MutableMapping

A case-insensitive dictionary-like object.

Implements all methods and operations of MutableMapping as well as dict’s copy. Also provides lower_items.

All keys are expected to be strings. The structure remembers the case of the last key to be set, and iter(instance), keys(), items() will contain case-sensitive keys. However, querying and contains testing is case insensitive:

cid = CaseInsensitiveDict() cid[‘Accept’] = ‘application/json’ cid[‘aCCEPT’] == ‘application/json’ # True list(cid) == [‘Accept’] # True

For example, headers['content-encoding'] will return the value of a 'Content-Encoding' response header, regardless of how the header name was originally stored.

Note

If the constructor, .update, or equality comparison operations are given keys that have equal .lower() values, the behavior is undefined.

lower_items()[source]

Like iteritems(), but with all lowercase keys.

Example:

>>> cid = CaseInsensitiveDict({'Content-Type': 'application/json'})
>>> list(cid.lower_items())
[('content-type', 'application/json')]
copy()[source]

orderedset

OrderedSet: Set that preserves insertion order with unique elements. Combines the uniqueness guarantee of sets with the ordering of lists.

class OrderedSet(iterable=None)[source]

Bases: MutableSet

A set that maintains insertion order using a doubly linked list.

Provides set operations while preserving the order elements were added.

Note

Based on Raymond Hettinger’s recipe from ActiveState.

Features:
  • Combines set behavior (unique elements) with list behavior (order preservation)

  • Supports all standard set operations (union, intersection, difference)

  • Maintains insertion order for iteration and representation

Example:

>>> s = OrderedSet('abracadaba')
>>> t = OrderedSet('simsalabim')
>>> (s | t)
OrderedSet(['a', 'b', 'r', 'c', 'd', 's', 'i', 'm', 'l'])
>>> (s & t)
OrderedSet(['a', 'b'])
>>> (s - t)
OrderedSet(['r', 'c', 'd'])
__init__(iterable=None)[source]

Initialize an OrderedSet with optional iterable.

Creates an empty ordered set or populates it from an iterable while preserving insertion order and removing duplicates.

Parameters:

iterable (Iterable[Any]) – Optional sequence of elements to add.

__len__()[source]

Return the number of elements in the set.

Returns:

Count of unique elements.

Return type:

int

__contains__(key)[source]

Check if an element exists in the set.

Parameters:

key (Any) – Element to check for membership.

Returns:

True if the element is in the set.

Return type:

bool

add(key)[source]

Add an element to the end of the set if not already present.

Parameters:

key (Any) – Element to add to the set.

Return type:

None

discard(key)[source]

Remove an element from the set if present.

Does not raise an error if element is not found.

Parameters:

key (Any) – Element to remove.

Return type:

None

__iter__()[source]

Iterate over elements in insertion order.

Returns:

Iterator yielding elements in order of addition.

Return type:

Iterator

__reversed__()[source]

Iterate over elements in reverse insertion order.

Returns:

Iterator yielding elements in reverse order.

Return type:

Iterator

pop(last=True)[source]

Remove and return an element from the set.

Parameters:

last (bool) – If True, remove from end; if False, from beginning.

Return type:

Any

Returns:

The removed element.

Raises:

KeyError – If the set is empty.

__repr__()[source]

Return string representation of the set.

Returns:

String showing class name and ordered elements.

Return type:

str

__eq__(other)[source]

Check equality with another set or OrderedSet.

For OrderedSet comparison, both content and order must match. For regular set comparison, only content is considered.

Parameters:

other (object) – Object to compare with.

Returns:

True if sets are equal.

Return type:

bool

heap

ComparableHeap: Heap queue with custom comparator key function. Useful when you need priority queue behavior with custom ordering.

class ComparableHeap(initial=None, key=<function ComparableHeap.<lambda>>)[source]

Bases: object

Heap with custom key comparator.

Wraps heapq to add a keyed comparator function.

Parameters:
  • initial (list) – Initial items for the heap.

  • key – Key function for comparison (default: identity).

Example:

>>> from datetime import datetime
>>> ch=ComparableHeap(initial=[                {'dtm':datetime(2017,1,1,12,10,59),'val':'one'},                {'dtm':datetime(2017,1,1,12,10,58),'val':'two'}],                key=lambda f: f['dtm'])
>>> ch.pop()
{'dtm': datetime.datetime(2017, 1, 1, 12, 10, 58), 'val': 'two'}
>>> ch.push({'val': 'three', 'dtm': datetime(2017,1,1,12,11,00)})
>>> ch.pop()
{'dtm': datetime.datetime(2017, 1, 1, 12, 10, 59), 'val': 'one'}
push(item)[source]
pop()[source]