Что это за операции над множествами и почему они дают разные результаты? - PullRequest
6 голосов
/ 06 февраля 2020

Я видел этот тестовый вопрос на Pluralsight:

Учитывая эти наборы:

x = {'a', 'b', 'c', 'd'}
y = {'c', 'e', 'f'}
z = {'a', 'g', 'h', 'i'}

Какое значение x | y ^ z?

Ожидаемый ответ: :

{'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'}

Объединяет наборы (автоматически отбрасывая дубликаты) и упорядочивает их от младшего к большему.

Мои вопросы:

  • Что это за выражение звонил?
  • Почему я получаю 3 разных результата из 3 разных Python версий?

Результат на Python 3.7.5 в Ubuntu 18.04:

{'c', 'h', 'f', 'd', 'b', 'i', 'g', 'a', 'e'}

Результат на Python 2.17.17rc1 на Ubuntu 18.04:

set(['a', 'c', 'b', 'e', 'd', 'g', 'f', 'i', 'h'])

Результат на Python 3.7.2 на Windows 10:

{'a', 'd', 'h', 'f', 'b', 'g', 'e', 'c', 'i'}

Вот ответ того же кода, который я использую для этого: https://repl.it/repls/RudeMoralWorkplace

Я хотел бы понять, что происходит за кулисами с этими выражениями, чтобы я мог разоблачить, почему я получить разные результаты.

1 Ответ

8 голосов
/ 06 февраля 2020

Упомянутые вами операции набора:

^ - симметрия c разница (XOR):

Вернуть новый набор с элементами либо в наборе, либо в другом, но не в обоих.

Пример: {'1', '2', '3'} ^ {'2', '3', '4'} = {'1', '4'}

| - union (OR):

Возвращает новый набор с элементами из набора и всеми другими.

Пример: {'1', '2', '3'} | {'2', '3', '4'} = {'1', '2', '3', '4'}

В python также есть другие операции над множествами:

& - пересечение (AND):

Вернуть новый набор с элементами, общими для набора и всех остальных.

Пример: {'1', '2', '3'} & {'2', '3', '4'} = {'2', '3'}

- - разница :

Возвращает новый набор с элементами в наборе, которых нет в других.

Пример: {'1', '2', '3'} - {'2', '3', '4'} = {'1'}

Порядок приоритета для этих операций -, &, ^, |, поэтому в вашем примере мы сначала применяем ^:

>>> y^z
{'a', 'c', 'e', 'f', 'g', 'h', 'i'}

А затем |:

>>> x|{'a', 'c', 'e', 'f', 'g', 'h', 'i'}
{'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i'}

Различные описываемые вами выходы на самом деле совпадают, поскольку наборы не упорядочены.

>>> {'c', 'h', 'f', 'd', 'b', 'i', 'g', 'a', 'e'} == {'a', 'd', 'h', 'f', 'b', 'g', 'e', 'c', 'i'}
True

Любой порядок, показанный в строковом представлении набора, является деталью реализации и на него не следует полагаться, так как он будет непредсказуемым, как вы обнаружили.

...