Skip to content

Instantly share code, notes, and snippets.

@akx
Created September 8, 2020 18:12
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save akx/889147fda1d5f4baa8a964a838eac509 to your computer and use it in GitHub Desktop.
Save akx/889147fda1d5f4baa8a964a838eac509 to your computer and use it in GitHub Desktop.
def make_immutable(v):
"""
Return an immutable representation of a mutable container.
The representation is only meant for machine use.
"""
if isinstance(v, (list, tuple)):
return (type(v), tuple(make_immutable(i) for i in v))
if isinstance(v, (set, frozenset)):
return (type(v), frozenset(make_immutable(i) for i in v))
if isinstance(v, dict):
return (type(v), tuple(make_immutable(pair) for pair in sorted(v.items())))
# Other types could be mutable, but we don't know how to handle them for now
return v
def deduplicate_mutable(seq):
seen = set()
for item in seq:
im_item = make_immutable(item)
if im_item not in seen:
yield item
seen.add(im_item)
seq = [
{1, 3, 7},
{7, 3, 1}, # sets are equal to each other
"hello!",
[[1, 3], [3, 1]],
[(1, 3), (3, 1)], # Not equal to the previous one; different types
[(1, 3), (3, 1)], # Equal to the previous one.
"hello!", # our old friend from before
{"hello": [1, 2, {"nested": "world"}]},
{"hello": [1, 2, {"nested": "world"}]},
]
for item in deduplicate_mutable(seq):
print(item)
# Prints out:
# {1, 3, 7}
# hello!
# [[1, 3], [3, 1]]
# [(1, 3), (3, 1)]
# {'hello': [1, 2, {'nested': 'world'}]}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment