Skip to content

Commit 7059880

Browse files
bpo-44646: Fix the hash of the union type. (GH-27179) (#27180)
It no longer depends on the order of arguments. hash(int | str) == hash(str | int) Co-authored-by: Jack DeVries <[email protected]> (cherry picked from commit aeaa553) Co-authored-by: Serhiy Storchaka <[email protected]>
1 parent 6aa59c6 commit 7059880

File tree

3 files changed

+12
-4
lines changed

3 files changed

+12
-4
lines changed

Lib/test/test_types.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -663,6 +663,10 @@ def test_or_types_operator(self):
663663
x.__args__ = [str, int]
664664
(int | str ) == x
665665

666+
def test_hash(self):
667+
self.assertEqual(hash(int | str), hash(str | int))
668+
self.assertEqual(hash(int | str), hash(typing.Union[int, str]))
669+
666670
def test_instancecheck(self):
667671
x = int | str
668672
self.assertIsInstance(1, x)
Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
Fix the hash of the union type: it no longer depends on the order of
2+
arguments.

Objects/unionobject.c

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,11 +33,13 @@ static Py_hash_t
3333
union_hash(PyObject *self)
3434
{
3535
unionobject *alias = (unionobject *)self;
36-
Py_hash_t h1 = PyObject_Hash(alias->args);
37-
if (h1 == -1) {
38-
return -1;
36+
PyObject *args = PyFrozenSet_New(alias->args);
37+
if (args == NULL) {
38+
return (Py_hash_t)-1;
3939
}
40-
return h1;
40+
Py_hash_t hash = PyObject_Hash(args);
41+
Py_DECREF(args);
42+
return hash;
4143
}
4244

4345
static int

0 commit comments

Comments
 (0)