Extracts the specific element matched by "item in container". Useful for interning or caching applications needing canonical or singleton values.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
class _CaptureEq: 'Object wrapper that remembers "other" for successful equality tests.' def __init__(self, obj): self.obj = obj self.match = obj def __eq__(self, other): result = (self.obj == other) if result: self.match = other return result def __getattr__(self, name): # support hash() or anything else needed by __contains__ return getattr(self.obj, name) def get_equivalent(container, item, default=None): '''Gets the specific container element matched by: "item in container". Useful for retreiving a canonical value equivalent to "item". For example, a caching or interning application may require fetching a single representative instance from many possible equivalent instances). >>> get_equivalent(set([1, 2, 3]), 2.0) # 2.0 is equivalent to 2 2 >>> get_equivalent([1, 2, 3], 4, default=0) 0 ''' t = _CaptureEq(item) if t in container: return t.match return default import doctest print doctest.testmod()
For applications that care about object identity, this recipes provides a fast way to extract specific dictionary keys and set elements equivalent to a given item.
Successful set and dictionary lookups using singleton values run quicker than lookups requiring a full equality test (internally, equality testing is bypassed for identical elements).
The recipe's running time is proportional to the performance of the "in" operator, O(1) for dictionaries and sets and O(n) for tuples and lists (with an early-out upon encountering the first match).
For applications needing an exception when the item is not found, change the last line of get_equivalent() to: raise KeyError(item)