-1

Using the python set add method i have noticed that the method sorts the content based on value and the content of the set.

Sample

Based on the docstring the following method description is found:

Docstring

Why is this happining ? And is there a method for this not to occur ?

I am using Python 3.6.

martineau
  • 119,623
  • 25
  • 170
  • 301
Isaque Fernando
  • 111
  • 1
  • 2
  • 2
    Please share code as text, not as image – azro Jul 08 '21 at 17:39
  • 1
    "unordered" means that is DOES NOT keeps the insertion order, and that you can't rely on that order, because it may change when executing the same code – azro Jul 08 '21 at 17:39
  • 1
    No @trincot. The question is based in another object. – Isaque Fernando Jul 08 '21 at 17:43
  • 1
    Does this answer your question? [Why don't Python sets preserve insertion order?](https://stackoverflow.com/questions/61414947/why-dont-python-sets-preserve-insertion-order) – trincot Jul 08 '21 at 17:46
  • The `set` class `__repr__()` method may simply be _listing_ the elements in a sorted order. Try using `for element in a:`, `print(element)` to see their actual order. – martineau Jul 08 '21 at 17:46
  • @martineau, the elements are printed in the same order as in `__repr__()` method. – Isaque Fernando Jul 08 '21 at 17:52
  • Could be a fluke. @PatrickArtner has a good suggestion to rule that out. – martineau Jul 08 '21 at 17:55

2 Answers2

1

Please don't count on this behavior:


>>> x = set()
>>> for i in range(10):
...     x.add(i)
... 
>>> x
{0, 1, 2, 3, 4, 5, 6, 7, 8, 9}
>>> for i in range(1000, 1020):
...     x.add(i)
... 
>>> x
{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 1000, 1001, 1002, 1003, 1004, 1005, 1006, 1007, 1008, 1009, 1010, 1011, 1012, 1013, 1014, 1015, 1016, 1017, 1018, 1019}
>>> x.remove(2)
>>> x
{0, 1, 3, 4, 5, 6, 7, 8, 9, 1000, 1001, 1002, 1003, 1004, 1005, 1006, 1007, 1008, 1009, 1010, 1011, 1012, 1013, 1014, 1015, 1016, 1017, 1018, 1019}
>>> x.add(2)
>>> x
{0, 1, 3, 4, 5, 6, 7, 8, 9, 2, 1000, 1001, 1002, 1003, 1004, 1005, 1006, 1007, 1008, 1009, 1010, 1011, 1012, 1013, 1014, 1015, 1016, 1017, 1018, 1019}
Yam Mesicka
  • 6,243
  • 7
  • 45
  • 64
0

Even if you see this "ordered" behavior once, does not mean it is always so. Trivial example:

w = set()
for i in range(100):
    w.add(i)
    w.add(str(i))

print(w)

Output:

{0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 
 17, 18, 19, 20, '20', 21, 22, 23, 24, 25, 26, 27, 28, 29, 
 30, 32, 33, 34, 35, 36, 37, '9', 38, 31, 39, 40, 41, 42, 
 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, '52', 53, 54, 55, 
 56, 57, 58, 59, 60, 61, '61', 62, 63, 64, '26', 65, 66, 
 67, '58', '36', 68, '6', '68', 69, '18', 71, 72, '4', 74, 
 75, 76, 77, '77', 79, 80, 81, 82, '12', '46', 85, 86, 87, 
 '33', 89, 90, 91, 92, 93, 94, 95, '23', '24', 98, 99, '49', 
 '92', '30', '44', '7', '21', '93', '86', '2', '67', '57', 
 '13', '79', '80', '96', '38', '32', '15', '45', '64', '83', 
 '65', '54', '88', '48', '75', '99', '71', '5', '0', '28', 
 '87', '43', '94', '90', '72', '42', '37', '59', '35', '8', 
 '17', '10', 70, 73, '98', '22', '19', '11', '27', '34', '14', 
 '56', '55', '69', '66', 78, '3', '1', '53', '84', '16', '25', 
 '76', 83, '82', '29', 84, '95', '31', '70', 88, '97', '40', 
 '47', '51', '85', '91', '60', '81', '89', 96, '78', '62', 
 '73', '74', 97, '41', '39', '50', '63'}

If it really sorted anything it should either

  • alternate the int or the string value (insert order)
  • show all ints sorted first, then all strings sorted

or some other kind of "detectable" pattern.

Using a very small samle set (range(10)) or very restricted values (all ints) can/might depending on the sets internal bucketing strategy lead to "ordered" outputs.

Patrick Artner
  • 50,409
  • 9
  • 43
  • 69