3

I need set-like data structure with these properties:

  • hashable
  • no duplicate elements
  • maintains order
  • immutable
  • iterable
  • part of standard library? want to keep it simple

What is happening:

frozenset([3,1,2,2,3]) -> frozenset(1,2,3)

What I need:

frozenset*([3,1,2,2,3]) -> frozenset*(3,1,2)

I thought I could use frozenset but both sets and frozensets reorder elements. I assume this is for faster duplicate checks? But in any case I can't have a reordering.

7
  • 3
    There is no such data structure in standard library. Commented Feb 12, 2021 at 18:51
  • 1
    Perhaps just use tuples, and ensure they have no duplicate elements at creation time. Commented Feb 12, 2021 at 19:16
  • " both sets and frozensets sort elements" no, they do not. Both of those data structures have no inherent order. Anything you see is an implementation detail in this case, most -- but not all -- integers simply hash to themselves, hence the apparent sorting Commented Feb 12, 2021 at 19:18
  • Anyway, what particular aspects of set objects do you require? Is fast-lookup the important part? that is the main set use-case. It sounds like you seem to only care about having no duplicates... Commented Feb 12, 2021 at 19:25
  • 1
    For example, on Python 3.7+, you could just use tuples and use a function to ensure no duplicates and maintain order (as already alluded to), so just: def no_dupe(data): return tuple(dict.fromkeys(data)) Commented Feb 12, 2021 at 19:34

2 Answers 2

4

As of Python 3.7 dicts no longer reorder elements and instead guarantee to preserve insertion order. You could use a dict where the keys are your set items and the values are ignored.

>>> dict.fromkeys([3,1,2,2,3])
{3: None, 1: None, 2: None}

Dicts aren't frozen, so if that's crucial then you could first put all the items into a dict and then build a tuple from the keys.

>>> tuple(dict.fromkeys([3,1,2,2,3]).keys())
(3, 1, 2)

This would be pretty close to a frozenset. The main difference is that it would take O(n) rather than O(1) time to check if an item is in the tuple.

Sign up to request clarification or add additional context in comments.

2 Comments

No need to call .keys
Right, it's optional. I prefer to be explicit here. (I'm not a fan of how iterating over a dictionary iterates over its keys. One of Python's rare missteps.)
2

There is no such implementation in the standard library

1 Comment

correct, but a pity...

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.