diff options
-rw-r--r-- | .SRCINFO | 6 | ||||
-rw-r--r-- | PKGBUILD | 12 | ||||
-rw-r--r-- | sagemath-gap-4.11.patch | 133 | ||||
-rw-r--r-- | sagemath-python-3.8.patch | 2574 |
4 files changed, 88 insertions, 2637 deletions
@@ -1,6 +1,6 @@ pkgbase = sagemath-git pkgdesc = Open Source Mathematics Software, free alternative to Magma, Maple, Mathematica, and Matlab - pkgver = 9.2.beta11.r0.gc353bce995 + pkgver = 9.2.beta12.r0.g5ec24db181 pkgrel = 1 url = http://www.sagemath.org arch = x86_64 @@ -98,7 +98,6 @@ pkgbase = sagemath-git source = test-optional.patch source = sagemath-cremona.patch source = sagemath-singular-4.1.2.patch - source = sagemath-python-3.8.patch source = sagemath-gap-4.11.patch source = sagemath-flint-2.6.patch sha256sums = SKIP @@ -107,8 +106,7 @@ pkgbase = sagemath-git sha256sums = 77aa8e99aae5da74a9486f01b603a0b5d224c3d13e9d9fab681fb71a6af149f1 sha256sums = 937074fa7a8a4e2aba9ea77ec622fe937985a1a9176c48460d51325ee877a4f5 sha256sums = 6f98488d0eb3a12b958cd1a34f85b7bee950ac756430371c1e134e564cbbf7d3 - sha256sums = 3bb1061af1b7beb113206b5c077a4e7c76aa782f412b8dd6ed86926cf28c481b - sha256sums = aeb6bb7a8d40f3d3b3547ee5f1e67e876051d9463cd1e0000b497c4d0f3e2fe9 + sha256sums = ae3c0c4412030224e7a911636a78a23e8835f49379557874b411e63dd876786f sha256sums = b881d4a6867a6f5360fd204e6a86fd27c6177c539b06f521402e2bcb5a6209cd pkgname = sagemath-git @@ -7,7 +7,7 @@ pkgbase=sagemath-git pkgname=(sagemath-git sagemath-jupyter-git) -pkgver=9.2.beta11.r0.gc353bce995 +pkgver=9.2.beta12.r0.g5ec24db181 pkgrel=1 pkgdesc="Open Source Mathematics Software, free alternative to Magma, Maple, Mathematica, and Matlab" arch=(x86_64) @@ -40,7 +40,6 @@ source=(git://git.sagemath.org/sage.git#branch=develop test-optional.patch sagemath-cremona.patch sagemath-singular-4.1.2.patch - sagemath-python-3.8.patch sagemath-gap-4.11.patch sagemath-flint-2.6.patch) sha256sums=('SKIP' @@ -49,8 +48,7 @@ sha256sums=('SKIP' '77aa8e99aae5da74a9486f01b603a0b5d224c3d13e9d9fab681fb71a6af149f1' '937074fa7a8a4e2aba9ea77ec622fe937985a1a9176c48460d51325ee877a4f5' '6f98488d0eb3a12b958cd1a34f85b7bee950ac756430371c1e134e564cbbf7d3' - '3bb1061af1b7beb113206b5c077a4e7c76aa782f412b8dd6ed86926cf28c481b' - 'aeb6bb7a8d40f3d3b3547ee5f1e67e876051d9463cd1e0000b497c4d0f3e2fe9' + 'ae3c0c4412030224e7a911636a78a23e8835f49379557874b411e63dd876786f' 'b881d4a6867a6f5360fd204e6a86fd27c6177c539b06f521402e2bcb5a6209cd') pkgver() { @@ -70,6 +68,8 @@ prepare(){ patch -p1 -i ../sagemath-singular-4.1.2.patch # Fix segfault and tests with flint 2.6 https://trac.sagemath.org/ticket/29719 patch -p1 -i ../sagemath-flint-2.6.patch +# Fix gap.version() and doctests with GAP 4.11 https://trac.sagemath.org/ticket/29314 + patch -p1 -i ../sagemath-gap-4.11.patch # Arch-specific patches # assume all optional packages are installed @@ -78,12 +78,8 @@ prepare(){ patch -p0 -i ../test-optional.patch # use correct latte-count binary name patch -p1 -i ../latte-count.patch -# Python 3.8 support - patch -p1 -i ../sagemath-python-3.8.patch # Fix mathjax path sed -e 's|mathjax|mathjax2|g' -i src/sage/env.py -# Fix gap.version() and doctests with GAP 4.11 - patch -p1 -i ../sagemath-gap-4.11.patch sed -e 's|sage-python23|python|' -i src/bin/* sed -e 's|$SAGE_PYTHON3|yes|' -i src/bin/sage diff --git a/sagemath-gap-4.11.patch b/sagemath-gap-4.11.patch index cba9b189a08b..601e2f721ec9 100644 --- a/sagemath-gap-4.11.patch +++ b/sagemath-gap-4.11.patch @@ -1,21 +1,8 @@ -diff --git a/src/sage/interfaces/gap.py b/src/sage/interfaces/gap.py -index 2b1cb8aef4..0bbc018499 100644 ---- a/src/sage/interfaces/gap.py -+++ b/src/sage/interfaces/gap.py -@@ -886,7 +886,7 @@ class Gap_generic(ExtraTabCompletion, Expect): - sage: print(gap.version()) - 4... - """ -- return self.eval('VERSION')[1:-1] -+ return self.eval('GAPInfo.Version')[1:-1] - - def function_call(self, function, args=None, kwds=None): - """ diff --git a/src/sage/coding/linear_code.py b/src/sage/coding/linear_code.py -index e106498063..b56388830b 100644 +index 8c330c7..b3901f8 100644 --- a/src/sage/coding/linear_code.py +++ b/src/sage/coding/linear_code.py -@@ -483,17 +483,17 @@ class AbstractLinearCode(AbstractCode, Module): +@@ -479,17 +479,17 @@ class AbstractLinearCode(AbstractLinearCodeNoMetric): 0 sage: C = codes.HammingCode(GF(4, 'z'), 3) sage: C.automorphism_group_gens() @@ -38,7 +25,7 @@ index e106498063..b56388830b 100644 Defn: z |--> z), ((z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1, z + 1); (), Ring endomorphism of Finite Field in z of size 2^2 Defn: z |--> z)], -@@ -709,10 +709,10 @@ class AbstractLinearCode(AbstractCode, Module): +@@ -705,10 +705,10 @@ class AbstractLinearCode(AbstractLinearCodeNoMetric): sage: C_iso == aut_group_can_label.get_canonical_form() True sage: aut_group_can_label.get_autom_gens() @@ -53,7 +40,7 @@ index e106498063..b56388830b 100644 Defn: z |--> z)] """ diff --git a/src/sage/combinat/tiling.py b/src/sage/combinat/tiling.py -index acc4640675..4ee841d681 100644 +index 3a70f13..e03fdd8 100644 --- a/src/sage/combinat/tiling.py +++ b/src/sage/combinat/tiling.py @@ -320,21 +320,21 @@ def ncube_isometry_group(n, orientation_preserving=True): @@ -90,21 +77,8 @@ index acc4640675..4ee841d681 100644 ] TESTS:: -diff --git a/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py b/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py -index b60931344c..0051f20652 100644 ---- a/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py -+++ b/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py -@@ -236,7 +236,7 @@ r""" - ~~~~~~~~~~~~~~~~~~~~~~ :: - - sage: G.Center() -- Group( [ ( 1, 3, 5)( 2, 4, 6) ] ) -+ Group( [ (1,3,5)(2,4,6) ] ) - - ~~~~~~~~~~~~~~~~~~~~~~ :: - diff --git a/src/sage/groups/finitely_presented.py b/src/sage/groups/finitely_presented.py -index 1642d48166..4d1dd4c548 100644 +index 1642d48..4d1dd4c 100644 --- a/src/sage/groups/finitely_presented.py +++ b/src/sage/groups/finitely_presented.py @@ -1201,7 +1201,7 @@ class FinitelyPresentedGroup(GroupMixinLibGAP, UniqueRepresentation, @@ -163,8 +137,34 @@ index 1642d48166..4d1dd4c548 100644 a*b^3*a^-1 ---> 1 sage: G([1,1,2,2,2]) +diff --git a/src/sage/groups/matrix_gps/finitely_generated.py b/src/sage/groups/matrix_gps/finitely_generated.py +index 2467582..ac0b7a3 100644 +--- a/src/sage/groups/matrix_gps/finitely_generated.py ++++ b/src/sage/groups/matrix_gps/finitely_generated.py +@@ -549,8 +549,8 @@ class FinitelyGeneratedMatrixGroup_gap(MatrixGroup_gap): + sage: MS = MatrixSpace(GF(2), 5, 5) + sage: A = MS([[0,0,0,0,1],[0,0,0,1,0],[0,0,1,0,0],[0,1,0,0,0],[1,0,0,0,0]]) + sage: G = MatrixGroup([A]) +- sage: G.as_permutation_group() +- Permutation Group with generators [(1,2)] ++ sage: G.as_permutation_group().order() ++ 2 + + A finite subgroup of GL(12,Z) as a permutation group:: + +@@ -624,8 +624,8 @@ class FinitelyGeneratedMatrixGroup_gap(MatrixGroup_gap): + sage: MG = GU(3,2).as_matrix_group() + sage: PG = MG.as_permutation_group() + sage: mg = MG.an_element() +- sage: PG(mg) +- (1,2,6,19,35,33)(3,9,26,14,31,23)(4,13,5)(7,22,17)(8,24,12)(10,16,32,27,20,28)(11,30,18)(15,25,36,34,29,21) ++ sage: PG(mg).order() # particular element depends on the set of GAP packages installed ++ 6 + """ + # Note that the output of IsomorphismPermGroup() depends on + # memory locations and will change if you change the order of diff --git a/src/sage/groups/perm_gps/permgroup.py b/src/sage/groups/perm_gps/permgroup.py -index 8512b01122..245fdd868b 100644 +index 334d90a..d7a0045 100644 --- a/src/sage/groups/perm_gps/permgroup.py +++ b/src/sage/groups/perm_gps/permgroup.py @@ -850,7 +850,7 @@ class PermutationGroup_generic(FiniteGroup): @@ -188,25 +188,56 @@ index 8512b01122..245fdd868b 100644 Another check for :trac:`5583`:: -diff --git a/src/sage/groups/matrix_gps/finitely_generated.py b/src/sage/groups/matrix_gps/finitely_generated.py -index d356c9cfc1..5f78373a3f 100644 ---- a/src/sage/groups/matrix_gps/finitely_generated.py -+++ b/src/sage/groups/matrix_gps/finitely_generated.py -@@ -550,7 +550,7 @@ class FinitelyGeneratedMatrixGroup_gap(MatrixGroup_gap): - sage: A = MS([[0,0,0,0,1],[0,0,0,1,0],[0,0,1,0,0],[0,1,0,0,0],[1,0,0,0,0]]) - sage: G = MatrixGroup([A]) - sage: G.as_permutation_group() -- Permutation Group with generators [(1,2)] -+ Permutation Group with generators [(2,17)(3,9)(4,25)(6,21)(7,13)(8,29)(10,19)(12,27)(14,23)(16,31)(20,26)(24,30)] +diff --git a/src/sage/interfaces/gap.py b/src/sage/interfaces/gap.py +index 123afb8..67e3bbf 100644 +--- a/src/sage/interfaces/gap.py ++++ b/src/sage/interfaces/gap.py +@@ -277,7 +277,7 @@ def get_gap_memory_pool_size(): + # Don't eat all address space if the user set ulimit -v + suggested_size = min(suggested_size, vmax // 10) + # ~220MB is the minimum for long doctests +- suggested_size = max(suggested_size, 250 * 1024**2) ++ suggested_size = max(suggested_size, 400 * 1024**2) + return suggested_size - A finite subgroup of GL(12,Z) as a permutation group:: -@@ -624,7 +624,7 @@ class FinitelyGeneratedMatrixGroup_gap(MatrixGroup_gap): - sage: PG = MG.as_permutation_group() - sage: mg = MG.an_element() - sage: PG(mg) -- (1,2,6,19,35,33)(3,9,26,14,31,23)(4,13,5)(7,22,17)(8,24,12)(10,16,32,27,20,28)(11,30,18)(15,25,36,34,29,21) -+ (2,33,32,23,31,55)(3,49,38,44,40,28)(4,17,59,62,58,46)(5,21,47,20,43,8)(6,53,50)(7,37,12,57,14,29)(9,41,56,34,64,10)(11,25,19)(13,61,26,51,22,15)(16,45,36)(18,27,35,48,52,54)(24,63,42)(30,39,60) +@@ -886,7 +886,7 @@ class Gap_generic(ExtraTabCompletion, Expect): + sage: print(gap.version()) + 4... """ - # Note that the output of IsomorphismPermGroup() depends on - # memory locations and will change if you change the order of +- return self.eval('VERSION')[1:-1] ++ return self.eval('GAPInfo.Version')[1:-1] + + def function_call(self, function, args=None, kwds=None): + """ +@@ -915,7 +915,7 @@ class Gap_generic(ExtraTabCompletion, Expect): + properly:: + + sage: g = Gap() +- sage: g.function_call("ConjugacyClassesSubgroups", sage.interfaces.gap.GapElement(g, 'SymmetricGroup(2)', name = 'a_variable_with_a_very_very_very_long_name')) ++ sage: g.function_call("ConjugacyClassesSubgroups", sage.interfaces.gap.GapElement(g, 'SymmetricGroup(2)', name = 'a_variable_with_a_very_very_very_long_name')) # random + [ ConjugacyClassSubgroups(SymmetricGroup( [ 1 .. 2 ] ),Group( () )), + ConjugacyClassSubgroups(SymmetricGroup( [ 1 .. 2 ] ),Group( [ (1,2) ] )) ] + +@@ -923,7 +923,7 @@ class Gap_generic(ExtraTabCompletion, Expect): + file to be communicated to GAP, this does not cause problems since + the file will contain a single command:: + +- sage: g.function_call("ConjugacyClassesSubgroups", sage.interfaces.gap.GapElement(g, 'SymmetricGroup(2)', name = 'a_variable_with_a_name_so_very_very_very_long_that_even_by_itself_will_make_expect_use_a_file')) ++ sage: g.function_call("ConjugacyClassesSubgroups", sage.interfaces.gap.GapElement(g, 'SymmetricGroup(2)', name = 'a_variable_with_a_name_so_very_very_very_long_that_even_by_itself_will_make_expect_use_a_file')) # random + [ ConjugacyClassSubgroups(SymmetricGroup( [ 1 .. 2 ] ),Group( () )), + ConjugacyClassSubgroups(SymmetricGroup( [ 1 .. 2 ] ),Group( [ (1,2) ] )) ] + """ +diff --git a/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py b/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py +index b609313..0051f20 100644 +--- a/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py ++++ b/src/sage/tests/books/judson-abstract-algebra/sylow-sage.py +@@ -236,7 +236,7 @@ r""" + ~~~~~~~~~~~~~~~~~~~~~~ :: + + sage: G.Center() +- Group( [ ( 1, 3, 5)( 2, 4, 6) ] ) ++ Group( [ (1,3,5)(2,4,6) ] ) + + ~~~~~~~~~~~~~~~~~~~~~~ :: + diff --git a/sagemath-python-3.8.patch b/sagemath-python-3.8.patch deleted file mode 100644 index 17e7e43303a2..000000000000 --- a/sagemath-python-3.8.patch +++ /dev/null @@ -1,2574 +0,0 @@ -diff --git a/src/sage/algebras/lie_algebras/structure_coefficients.py b/src/sage/algebras/lie_algebras/structure_coefficients.py -index 822da88..cc84cac 100644 ---- a/src/sage/algebras/lie_algebras/structure_coefficients.py -+++ b/src/sage/algebras/lie_algebras/structure_coefficients.py -@@ -124,7 +124,7 @@ class LieAlgebraWithStructureCoefficients(FinitelyGeneratedLieAlgebra, IndexedGe - try: - s_coeff = {(d[k[0]], d[k[1]]): [(d[x], y) for x,y in get_pairs(s_coeff[k])] - for k in s_coeff} -- except KeyError: -+ except (KeyError, ValueError): - # At this point we assume they are given by the index set - pass - -diff --git a/src/sage/categories/coxeter_groups.py b/src/sage/categories/coxeter_groups.py -index eec89a3..2039ad4 100644 ---- a/src/sage/categories/coxeter_groups.py -+++ b/src/sage/categories/coxeter_groups.py -@@ -279,8 +279,8 @@ class CoxeterGroups(Category_singleton): - sage: sorted(W.braid_orbit(word)) - [[0, 1, 2, 1], [0, 2, 1, 2], [2, 0, 1, 2]] - -- sage: W.braid_orbit([2,1,1,2,1]) -- [[2, 2, 1, 2, 2], [2, 1, 1, 2, 1], [1, 2, 1, 1, 2], [2, 1, 2, 1, 2]] -+ sage: sorted(W.braid_orbit([2,1,1,2,1])) -+ [[1, 2, 1, 1, 2], [2, 1, 1, 2, 1], [2, 1, 2, 1, 2], [2, 2, 1, 2, 2]] - - sage: W = ReflectionGroup(['A',3], index_set=["AA","BB",5]) # optional - gap3 - sage: w = W.long_element() # optional - gap3 -diff --git a/src/sage/categories/finite_enumerated_sets.py b/src/sage/categories/finite_enumerated_sets.py -index 0c85310..9debe13 100644 ---- a/src/sage/categories/finite_enumerated_sets.py -+++ b/src/sage/categories/finite_enumerated_sets.py -@@ -289,14 +289,14 @@ class FiniteEnumeratedSets(CategoryWithAxiom): - sage: C = Example() - sage: list(C) - hello! -- hello! -+ ... - [1, 2, 3] - sage: list(C) - hello! -- hello! -+ ... - [1, 2, 3] - -- Note that ``hello!`` actually gets printed twice in -+ Note that ``hello!`` actually gets printed more than once in - the calls to ``list(C)``. That's because of the - implicit calls to :meth:`__len__`, which also relies - on :meth:`__iter__`. Let's call :meth:`list`:: -diff --git a/src/sage/categories/homset.py b/src/sage/categories/homset.py -index d3d2896..22df819 100644 ---- a/src/sage/categories/homset.py -+++ b/src/sage/categories/homset.py -@@ -586,11 +586,10 @@ class Homset(Set_generic): - - sage: X = ZZ['x']; X.rename("X") - sage: Y = ZZ['y']; Y.rename("Y") -+ sage: f = X.hom([0], Y) - sage: class MyHomset(Homset): -- ....: def my_function(self, x): -- ....: return Y(x[0]) - ....: def _an_element_(self): -- ....: return sage.categories.morphism.SetMorphism(self, self.my_function) -+ ....: return sage.categories.morphism.SetMorphism(self, f) - sage: import __main__; __main__.MyHomset = MyHomset # fakes MyHomset being defined in a Python module - sage: H = MyHomset(X, Y, category=Monoids(), base = ZZ) - sage: H -@@ -602,9 +601,6 @@ class Homset(Set_generic): - ... - TypeError: category (=1) must be a category - -- sage: H -- Set of Morphisms from X to Y in Category of monoids -- sage: TestSuite(H).run() - sage: H = MyHomset(X, Y, category=1, base = ZZ, check = False) - Traceback (most recent call last): - ... -@@ -1239,11 +1235,10 @@ class HomsetWithBase(Homset): - - sage: X = ZZ['x']; X.rename("X") - sage: Y = ZZ['y']; Y.rename("Y") -+ sage: f = X.hom([0], Y) - sage: class MyHomset(HomsetWithBase): -- ....: def my_function(self, x): -- ....: return Y(x[0]) - ....: def _an_element_(self): -- ....: return sage.categories.morphism.SetMorphism(self, self.my_function) -+ ....: return sage.categories.morphism.SetMorphism(self, f) - sage: import __main__; __main__.MyHomset = MyHomset # fakes MyHomset being defined in a Python module - sage: H = MyHomset(X, Y, category=Monoids()) - sage: H -diff --git a/src/sage/combinat/blob_algebra.py b/src/sage/combinat/blob_algebra.py -index 8d719b2..00d3376 100644 ---- a/src/sage/combinat/blob_algebra.py -+++ b/src/sage/combinat/blob_algebra.py -@@ -325,27 +325,27 @@ class BlobDiagrams(Parent, UniqueRepresentation): - - sage: from sage.combinat.blob_algebra import BlobDiagrams - sage: BD3 = BlobDiagrams(3) -- sage: for b in BD3: b -- ({}, {{-3, 3}, {-2, -1}, {1, 2}}) -- ({{1, 2}}, {{-3, 3}, {-2, -1}}) -- ({{-2, -1}}, {{-3, 3}, {1, 2}}) -- ({{-2, -1}, {1, 2}}, {{-3, 3}}) -- ({{-3, 3}}, {{-2, -1}, {1, 2}}) -- ({{-3, 3}, {1, 2}}, {{-2, -1}}) -- ({{-3, 3}, {-2, -1}}, {{1, 2}}) -- ({{-3, 3}, {-2, -1}, {1, 2}}, {}) -- ({}, {{-3, -2}, {-1, 3}, {1, 2}}) -- ({{1, 2}}, {{-3, -2}, {-1, 3}}) -- ({{-1, 3}}, {{-3, -2}, {1, 2}}) -- ({{-1, 3}, {1, 2}}, {{-3, -2}}) -- ({}, {{-3, 1}, {-2, -1}, {2, 3}}) -- ({{-3, 1}}, {{-2, -1}, {2, 3}}) -- ({{-2, -1}}, {{-3, 1}, {2, 3}}) -- ({{-3, 1}, {-2, -1}}, {{2, 3}}) -- ({}, {{-3, -2}, {-1, 1}, {2, 3}}) -- ({{-1, 1}}, {{-3, -2}, {2, 3}}) -- ({}, {{-3, 3}, {-2, 2}, {-1, 1}}) -- ({{-1, 1}}, {{-3, 3}, {-2, 2}}) -+ sage: sorted(BD3) -+ [({}, {{-3, -2}, {-1, 1}, {2, 3}}), -+ ({}, {{-3, -2}, {-1, 3}, {1, 2}}), -+ ({}, {{-3, 1}, {-2, -1}, {2, 3}}), -+ ({}, {{-3, 3}, {-2, -1}, {1, 2}}), -+ ({}, {{-3, 3}, {-2, 2}, {-1, 1}}), -+ ({{-3, 1}}, {{-2, -1}, {2, 3}}), -+ ({{-3, 3}}, {{-2, -1}, {1, 2}}), -+ ({{-2, -1}}, {{-3, 1}, {2, 3}}), -+ ({{-2, -1}}, {{-3, 3}, {1, 2}}), -+ ({{-1, 1}}, {{-3, -2}, {2, 3}}), -+ ({{-1, 1}}, {{-3, 3}, {-2, 2}}), -+ ({{-1, 3}}, {{-3, -2}, {1, 2}}), -+ ({{1, 2}}, {{-3, -2}, {-1, 3}}), -+ ({{1, 2}}, {{-3, 3}, {-2, -1}}), -+ ({{-3, 1}, {-2, -1}}, {{2, 3}}), -+ ({{-3, 3}, {-2, -1}}, {{1, 2}}), -+ ({{-3, 3}, {1, 2}}, {{-2, -1}}), -+ ({{-2, -1}, {1, 2}}, {{-3, 3}}), -+ ({{-1, 3}, {1, 2}}, {{-3, -2}}), -+ ({{-3, 3}, {-2, -1}, {1, 2}}, {})] - """ - for D in DyckWords(self._n): - markable = set() -@@ -398,12 +398,12 @@ class BlobAlgebra(CombinatorialFreeModule): - - sage: R.<q,r,s> = ZZ[] - sage: B4 = algebras.Blob(4, q, r, s) -- sage: B = list(B4.basis()) -- sage: B[2] -+ sage: B = sorted(B4.basis()) -+ sage: B[14] - B({{-4, -3}}, {{-2, -1}, {1, 2}, {3, 4}}) -- sage: B[4] -+ sage: B[40] - B({{3, 4}}, {{-4, -3}, {-2, -1}, {1, 2}}) -- sage: B[2] * B[4] -+ sage: B[14] * B[40] - q*r*s*B({}, {{-4, -3}, {-2, -1}, {1, 2}, {3, 4}}) - - REFERENCES: -@@ -583,12 +583,12 @@ class BlobAlgebra(CombinatorialFreeModule): - sage: R.<q,r,s> = ZZ[] - sage: B4 = algebras.Blob(4, q, r, s) - sage: B = B4.basis() -- sage: BD = B.keys() -- sage: BD[2] -+ sage: BD = sorted(B.keys()) -+ sage: BD[14] - ({{-4, -3}}, {{-2, -1}, {1, 2}, {3, 4}}) -- sage: BD[4] -+ sage: BD[40] - ({{3, 4}}, {{-4, -3}, {-2, -1}, {1, 2}}) -- sage: B4.product_on_basis(BD[2], BD[4]) -+ sage: B4.product_on_basis(BD[14], BD[40]) - q*r*s*B({}, {{-4, -3}, {-2, -1}, {1, 2}, {3, 4}}) - sage: all(len((x*y).support()) == 1 for x in B for y in B) - True -diff --git a/src/sage/combinat/cluster_algebra_quiver/mutation_class.py b/src/sage/combinat/cluster_algebra_quiver/mutation_class.py -index 0105e82..a88346e 100644 ---- a/src/sage/combinat/cluster_algebra_quiver/mutation_class.py -+++ b/src/sage/combinat/cluster_algebra_quiver/mutation_class.py -@@ -508,8 +508,8 @@ def _graph_without_edge_labels(dg, vertices): - """ - vertices = list(vertices) - edges = dg.edge_iterator(labels=True) -- edge_labels = tuple(set(label for _, _, label in edges -- if label != (1, -1))) -+ edge_labels = tuple(sorted(set(label for _, _, label in edges -+ if label != (1, -1)))) - edge_partition = [[] for _ in edge_labels] - i = 0 - while i in vertices: -diff --git a/src/sage/combinat/colored_permutations.py b/src/sage/combinat/colored_permutations.py -index 2227ee6..0f2a739 100644 ---- a/src/sage/combinat/colored_permutations.py -+++ b/src/sage/combinat/colored_permutations.py -@@ -46,9 +46,8 @@ class ColoredPermutation(MultiplicativeGroupElement): - - sage: C = ColoredPermutations(4, 3) - sage: s1,s2,t = C.gens() -- sage: hash(s1), hash(s2), hash(t) -- (2666658751600856334, 3639282354432100950, 3639281107336048003) # 64-bit -- (-1973744370, 88459862, -1467077245) # 32-bit -+ sage: for gen in s1,s2,t: -+ ....: assert hash(gen) ^^ hash(gen._colors) == hash(gen._perm) - """ - return hash(self._perm) ^ hash(self._colors) - -diff --git a/src/sage/combinat/constellation.py b/src/sage/combinat/constellation.py -index 4efb824..e81f747 100644 ---- a/src/sage/combinat/constellation.py -+++ b/src/sage/combinat/constellation.py -@@ -218,9 +218,8 @@ class Constellation_class(Element): - EXAMPLES:: - - sage: c = Constellation(([0,2,1],[2,1,0],[1,2,0]), mutable=False) -- sage: c.__hash__() -- 5481133608926415725 # 64-bit -- 511937389 # 32-bit -+ sage: hash(c) == hash(tuple(c._g)) -+ True - """ - if self._mutable: - raise ValueError("can not hash mutable constellation") -diff --git a/src/sage/combinat/e_one_star.py b/src/sage/combinat/e_one_star.py -index 04fbe15..08ea6ca 100644 ---- a/src/sage/combinat/e_one_star.py -+++ b/src/sage/combinat/e_one_star.py -@@ -886,8 +886,8 @@ class Patch(SageObject): - - sage: from sage.combinat.e_one_star import Face, Patch - sage: P = Patch([Face((0,0,0),1), Face((1,2,0),3), Face((1,2,0),1)]) -- sage: P.faces_of_vector([1,2,0]) -- [[(1, 2, 0), 3]*, [(1, 2, 0), 1]*] -+ sage: sorted(P.faces_of_vector([1,2,0])) -+ [[(1, 2, 0), 1]*, [(1, 2, 0), 3]*] - """ - v = vector(v) - return [f for f in self if f.vector() == v] -@@ -904,7 +904,7 @@ class Patch(SageObject): - - sage: from sage.combinat.e_one_star import Face, Patch - sage: P = Patch([Face((0,0,0),1), Face((1,2,0),3), Face((1,2,0),1)]) -- sage: P.faces_of_type(1) -+ sage: sorted(P.faces_of_type(1)) - [[(0, 0, 0), 1]*, [(1, 2, 0), 1]*] - """ - return [f for f in self if f.type() == t] -@@ -921,7 +921,7 @@ class Patch(SageObject): - - sage: from sage.combinat.e_one_star import Face, Patch - sage: P = Patch([Face((0,0,0),1, 'red'), Face((1,2,0),3, 'blue'), Face((1,2,0),1, 'red')]) -- sage: P.faces_of_color('red') -+ sage: sorted(P.faces_of_color('red')) - [[(0, 0, 0), 1]*, [(1, 2, 0), 1]*] - """ - color = tuple(Color(color)) -diff --git a/src/sage/combinat/finite_state_machine.py b/src/sage/combinat/finite_state_machine.py -index 8c03a0a..6bbafd6 100644 ---- a/src/sage/combinat/finite_state_machine.py -+++ b/src/sage/combinat/finite_state_machine.py -@@ -1760,7 +1760,7 @@ class FSMState(SageObject): - sage: B = deepcopy(A) - sage: B - (1, 3) -- sage: B.label == A.label -+ sage: B.label() == A.label() - True - sage: B.label is A.label - False -diff --git a/src/sage/combinat/growth.py b/src/sage/combinat/growth.py -index d26bf37..0fbe87b 100644 ---- a/src/sage/combinat/growth.py -+++ b/src/sage/combinat/growth.py -@@ -1707,7 +1707,7 @@ class Rule(UniqueRepresentation): - EXAMPLES:: - - sage: from sage.combinat.growth import Rule -- sage: Rule().normalize_vertex("hello") is "hello" -+ sage: Rule().normalize_vertex("hello") == "hello" - True - """ - return v -diff --git a/src/sage/combinat/posets/incidence_algebras.py b/src/sage/combinat/posets/incidence_algebras.py -index 162a539..65dc086 100644 ---- a/src/sage/combinat/posets/incidence_algebras.py -+++ b/src/sage/combinat/posets/incidence_algebras.py -@@ -156,10 +156,12 @@ class IncidenceAlgebra(CombinatorialFreeModule): - - sage: P = posets.BooleanLattice(1) - sage: I = P.incidence_algebra(QQ) -- sage: I.some_elements() -+ sage: Ielts = I.some_elements(); Ielts # random - [2*I[0, 0] + 2*I[0, 1] + 3*I[1, 1], - I[0, 0] - I[0, 1] + I[1, 1], - I[0, 0] + I[0, 1] + I[1, 1]] -+ sage: [a in I for a in Ielts] -+ [True, True, True] - """ - return [self.an_element(), self.moebius(), self.zeta()] - -diff --git a/src/sage/combinat/posets/posets.py b/src/sage/combinat/posets/posets.py -index fd2a182..bc7e62b 100644 ---- a/src/sage/combinat/posets/posets.py -+++ b/src/sage/combinat/posets/posets.py -@@ -8180,10 +8180,14 @@ class FinitePoset(UniqueRepresentation, Parent): - - sage: P = posets.AntichainPoset(3) - sage: Pc = P.cuts() -- sage: [list(c) for c in Pc] -- [[0], [], [0, 1, 2], [2], [1]] -- sage: Pc[0] -- frozenset({0}) -+ sage: Pc # random -+ [frozenset({0}), -+ frozenset(), -+ frozenset({0, 1, 2}), -+ frozenset({2}), -+ frozenset({1})] -+ sage: sorted(list(c) for c in Pc) -+ [[], [0], [0, 1, 2], [1], [2]] - - .. SEEALSO:: - -diff --git a/src/sage/combinat/rigged_configurations/tensor_product_kr_tableaux.py b/src/sage/combinat/rigged_configurations/tensor_product_kr_tableaux.py -index 2691066..8571c2a 100644 ---- a/src/sage/combinat/rigged_configurations/tensor_product_kr_tableaux.py -+++ b/src/sage/combinat/rigged_configurations/tensor_product_kr_tableaux.py -@@ -328,9 +328,9 @@ class TensorProductOfKirillovReshetikhinTableaux(FullTensorProductOfRegularCryst - - sage: KRT = crystals.TensorProductOfKirillovReshetikhinTableaux(['A', 3, 1], [[2,1], [1,1]]) - sage: g = KRT.__iter__() -- sage: next(g) -+ sage: next(g) # random - [[2], [3]] (X) [[1]] -- sage: next(g) -+ sage: next(g) # random - [[2], [4]] (X) [[1]] - """ - index_set = self._cartan_type.classical().index_set() -diff --git a/src/sage/combinat/rooted_tree.py b/src/sage/combinat/rooted_tree.py -index f12c6c1..ace4009 100644 ---- a/src/sage/combinat/rooted_tree.py -+++ b/src/sage/combinat/rooted_tree.py -@@ -256,9 +256,8 @@ class RootedTree(AbstractClonableTree, NormalizedClonableList, - EXAMPLES:: - - sage: RT = RootedTree -- sage: hash(RT([[],[[]]])) # indirect doctest -- 2578595415271398032 # 64-bit -- 1119083152 # 32-bit -+ sage: hash(RT([[],[[]]])) == hash((2, 0, 1, 0)) # indirect doctest -+ True - """ - return hash(self.sort_key()) - -@@ -953,9 +952,8 @@ class LabelledRootedTree(AbstractLabelledClonableTree, RootedTree): - EXAMPLES:: - - sage: lb = RootedTrees()([[],[[], []]]).canonical_labelling() -- sage: hash(lb) # indirect doctest -- 686798862222558969 # 64-bit -- 652936953 # 32-bit -+ sage: hash(lb) == hash(((2, 1), (0, 2), (2, 3), (0, 4), (0, 5))) # indirect doctest -+ True - """ - return hash(self.sort_key()) - -diff --git a/src/sage/combinat/similarity_class_type.py b/src/sage/combinat/similarity_class_type.py -index ec3676a..55ec1fb 100644 ---- a/src/sage/combinat/similarity_class_type.py -+++ b/src/sage/combinat/similarity_class_type.py -@@ -408,15 +408,14 @@ class PrimarySimilarityClassType(Element, - sage: PT1 = PrimarySimilarityClassType(2, [3, 2, 1]) - sage: PT2 = PrimarySimilarityClassType(3, [3, 2, 1]) - sage: PT3 = PrimarySimilarityClassType(2, [4, 2, 1]) -- sage: hash(PT1) -- 5050909583595644741 # 64-bit -- 1658169157 # 32-bit -- sage: hash(PT2) -- 5050909583595644740 # 64-bit -- 1658169156 # 32-bit -- sage: hash(PT3) -- 6312110366011971308 # 64-bit -- 1429493484 # 32-bit -+ sage: hash(PT1) == hash(PrimarySimilarityClassType(2, [3, 2, 1])) -+ True -+ sage: abs(hash(PT1) - hash(PT2)) == 1 -+ True -+ sage: hash(PT1) == hash(PT3) -+ False -+ sage: hash(PT2) == hash(PT3) -+ False - """ - return hash(self._deg) ^ hash(tuple(self._par)) - -diff --git a/src/sage/combinat/subsets_pairwise.py b/src/sage/combinat/subsets_pairwise.py -index b126c5c..aeceb70 100644 ---- a/src/sage/combinat/subsets_pairwise.py -+++ b/src/sage/combinat/subsets_pairwise.py -@@ -120,7 +120,7 @@ class PairwiseCompatibleSubsets(RecursivelyEnumeratedSet_forest): - sage: P == P - True - """ -- return self.__class__ is other.__class__ and self._ambient == other._ambient and self._predicate == other._predicate -+ return self.__class__ is other.__class__ and self._ambient == other._ambient and self._predicate.__str__() == other._predicate.__str__() - - def __contains__(self, subset): - """ -diff --git a/src/sage/combinat/symmetric_group_representations.py b/src/sage/combinat/symmetric_group_representations.py -index 554b161..4e2d817 100644 ---- a/src/sage/combinat/symmetric_group_representations.py -+++ b/src/sage/combinat/symmetric_group_representations.py -@@ -292,9 +292,8 @@ class SymmetricGroupRepresentation_generic_class(SageObject): - TESTS:: - - sage: spc1 = SymmetricGroupRepresentation([3], cache_matrices=True) -- sage: hash(spc1) -- -1137003014 # 32-bit -- 3430541866490 # 64-bit -+ sage: hash(spc1) ^^ hash((3,)) == hash(ZZ) -+ True - """ - return hash(self._ring) ^ hash(self._partition) - -diff --git a/src/sage/combinat/words/word_infinite_datatypes.py b/src/sage/combinat/words/word_infinite_datatypes.py -index 078f006..a42901c 100644 ---- a/src/sage/combinat/words/word_infinite_datatypes.py -+++ b/src/sage/combinat/words/word_infinite_datatypes.py -@@ -289,14 +289,14 @@ class WordDatatype_callable(WordDatatype): - sage: w = Word(lambda n : n%3+10, caching=False) - sage: w.__reduce__() - (Infinite words over Set of Python objects of class 'object', -- (...csage.misc.fpickle...<lambda>..., 'pickled_function', False)) -+ (...sage.misc.fpickle...<lambda>..., 'pickled_function', False)) - - :: - - sage: w = Word(lambda n : n%3+10, caching=False, length=8) - sage: w.__reduce__() - (Finite words over Set of Python objects of class 'object', -- (...csage.misc.fpickle...<lambda>..., 8, 'pickled_function', False)) -+ (...sage.misc.fpickle...<lambda>..., 8, 'pickled_function', False)) - """ - from sage.misc.fpickle import pickle_function - try: -@@ -528,14 +528,14 @@ class WordDatatype_callable_with_caching(WordDatatype_callable): - sage: w = Word(lambda n : n%3+10, caching=True) - sage: w.__reduce__() - (Infinite words over Set of Python objects of class 'object', -- (...csage.misc.fpickle...<lambda>..., 'pickled_function', True)) -+ (...sage.misc.fpickle...<lambda>..., 'pickled_function', True)) - - :: - - sage: w = Word(lambda n : n%3+10, caching=True, length=8) - sage: w.__reduce__() - (Finite words over Set of Python objects of class 'object', -- (...csage.misc.fpickle...<lambda>..., 8, 'pickled_function', True)) -+ (...sage.misc.fpickle...<lambda>..., 8, 'pickled_function', True)) - - Because ``pickle_function`` fails on CallableFromListOfWords, - then concatenation of words are expanded as a list:: -diff --git a/src/sage/combinat/yang_baxter_graph.py b/src/sage/combinat/yang_baxter_graph.py -index b3e56f7..a3ca165 100644 ---- a/src/sage/combinat/yang_baxter_graph.py -+++ b/src/sage/combinat/yang_baxter_graph.py -@@ -336,7 +336,8 @@ class YangBaxterGraph_generic(SageObject): - seen[self._root] = True - while queue: - u = queue.pop() -- for w in digraph.neighbor_out_iterator(u): -+ l = sorted(list(digraph.neighbor_out_iterator(u))) -+ for w in l: - if w not in seen: - seen[w] = True - queue.append(w) -@@ -380,7 +381,7 @@ class YangBaxterGraph_generic(SageObject): - sage: Y = YangBaxterGraph(root=(1,0,2,1,0), operators=ops) - sage: Y.successors(Y.root()) - [(1, 2, 0, 1, 0)] -- sage: Y.successors((1, 2, 0, 1, 0)) -+ sage: sorted(Y.successors((1, 2, 0, 1, 0))) - [(1, 2, 1, 0, 0), (2, 1, 0, 1, 0)] - """ - return [a for (a,b) in self._successors(v)] -diff --git a/src/sage/data_structures/mutable_poset.py b/src/sage/data_structures/mutable_poset.py -index 6df1357..a334c5e 100644 ---- a/src/sage/data_structures/mutable_poset.py -+++ b/src/sage/data_structures/mutable_poset.py -@@ -3315,7 +3315,7 @@ class MutablePoset(SageObject): - ....: return all(l <= r for l, r in zip(left, right)) - sage: P = MP([T((1, 1)), T((1, 3)), T((2, 1)), - ....: T((1, 2)), T((2, 2))]) -- sage: list(P.maximal_elements()) -+ sage: sorted(P.maximal_elements()) - [(1, 3), (2, 2)] - - .. SEEALSO:: -diff --git a/src/sage/doctest/external.py b/src/sage/doctest/external.py -index b0db07b..5c5abe4 100644 ---- a/src/sage/doctest/external.py -+++ b/src/sage/doctest/external.py -@@ -25,7 +25,15 @@ AUTHORS: - # http://www.gnu.org/licenses/ - #***************************************************************************** - --from multiprocessing import Array -+import multiprocessing -+import os -+ -+# With OS X, Python 3.8 defaults to use 'spawn' instead of 'fork' in -+# multiprocessing, and Sage doctesting doesn't work with 'spawn'. See -+# trac #27754. -+if os.uname().sysname == 'Darwin': -+ multiprocessing.set_start_method('fork', force=True) -+Array = multiprocessing.Array - - import urllib.error - from urllib.request import Request, urlopen -diff --git a/src/sage/doctest/forker.py b/src/sage/doctest/forker.py -index bd7860a..cb36676 100644 ---- a/src/sage/doctest/forker.py -+++ b/src/sage/doctest/forker.py -@@ -63,6 +63,11 @@ from sage.repl.user_globals import set_globals - from sage.cpython.atexit import restore_atexit - from sage.cpython.string import bytes_to_str, str_to_bytes - -+# With OS X, Python 3.8 defaults to use 'spawn' instead of 'fork' in -+# multiprocessing, and Sage doctesting doesn't work with 'spawn'. See -+# trac #27754. -+if os.uname().sysname == 'Darwin': -+ multiprocessing.set_start_method('fork', force=True) - - # All doctests run as if the following future imports are present - import __future__ -@@ -1093,7 +1098,8 @@ class SageDocTestRunner(doctest.DocTestRunner, object): - False - sage: doctests, extras = FDS.create_doctests(globs) - sage: ex0 = doctests[0].examples[0] -- sage: compiler = lambda ex: compile(ex.source, '<doctest sage.doctest.forker[0]>', 'single', 32768, 1) -+ sage: flags = 32768 if sys.version_info.minor < 8 else 524288 -+ sage: compiler = lambda ex: compile(ex.source, '<doctest sage.doctest.forker[0]>', 'single', flags, 1) - sage: DTR.compile_and_execute(ex0, compiler, globs) - 1764 - sage: globs['doctest_var'] -@@ -1106,7 +1112,7 @@ class SageDocTestRunner(doctest.DocTestRunner, object): - Now we can execute some more doctests to see the dependencies. :: - - sage: ex1 = doctests[0].examples[1] -- sage: compiler = lambda ex:compile(ex.source, '<doctest sage.doctest.forker[1]>', 'single', 32768, 1) -+ sage: compiler = lambda ex:compile(ex.source, '<doctest sage.doctest.forker[1]>', 'single', flags, 1) - sage: DTR.compile_and_execute(ex1, compiler, globs) - sage: sorted(list(globs.set)) - ['R', 'a'] -@@ -1118,7 +1124,7 @@ class SageDocTestRunner(doctest.DocTestRunner, object): - :: - - sage: ex2 = doctests[0].examples[2] -- sage: compiler = lambda ex:compile(ex.source, '<doctest sage.doctest.forker[2]>', 'single', 32768, 1) -+ sage: compiler = lambda ex:compile(ex.source, '<doctest sage.doctest.forker[2]>', 'single', flags, 1) - sage: DTR.compile_and_execute(ex2, compiler, globs) - a + 42 - sage: list(globs.set) -@@ -2354,7 +2360,7 @@ class DocTestWorker(multiprocessing.Process): - True - sage: W.killed - True -- sage: time.sleep(0.2) # Worker doesn't die -+ sage: time.sleep(float(0.2)) # Worker doesn't die - sage: W.kill() # Worker dies now - True - sage: time.sleep(1) -diff --git a/src/sage/doctest/util.py b/src/sage/doctest/util.py -index cd1706e..c66a75d 100644 ---- a/src/sage/doctest/util.py -+++ b/src/sage/doctest/util.py -@@ -127,7 +127,7 @@ class Timer: - sage: from sage.doctest.util import Timer - sage: import time - sage: timer = Timer().start() -- sage: time.sleep(0.5) -+ sage: time.sleep(float(0.5)) - sage: timer.stop() - {'cputime': ..., 'walltime': ...} - """ -diff --git a/src/sage/dynamics/arithmetic_dynamics/generic_ds.py b/src/sage/dynamics/arithmetic_dynamics/generic_ds.py -index 0825e41..c772b3f 100644 ---- a/src/sage/dynamics/arithmetic_dynamics/generic_ds.py -+++ b/src/sage/dynamics/arithmetic_dynamics/generic_ds.py -@@ -476,16 +476,16 @@ class DynamicalSystem(SchemeMorphism_polynomial, - [(0 : 1), (1 : 0), (1 : 1)] - sage: N.<a> = f.field_of_definition_periodic(3); N - Number Field in a with defining polynomial x^6 + x^5 + x^4 + x^3 + x^2 + x + 1 -- sage: f.periodic_points(3,minimal=False, R=N) -- [(0 : 1), -+ sage: sorted(f.periodic_points(3,minimal=False, R=N), key=str) -+ [(-a^5 - a^4 - a^3 - a^2 - a - 1 : 1), -+ (0 : 1), -+ (1 : 0), -+ (1 : 1), - (a : 1), -- (a^5 : 1), - (a^2 : 1), -- (-a^5 - a^4 - a^3 - a^2 - a - 1 : 1), -- (a^4 : 1), -- (1 : 0), - (a^3 : 1), -- (1 : 1)] -+ (a^4 : 1), -+ (a^5 : 1)] - - :: - -diff --git a/src/sage/dynamics/arithmetic_dynamics/projective_ds.py b/src/sage/dynamics/arithmetic_dynamics/projective_ds.py -index 878ec1f..68ba38f 100644 ---- a/src/sage/dynamics/arithmetic_dynamics/projective_ds.py -+++ b/src/sage/dynamics/arithmetic_dynamics/projective_ds.py -@@ -3145,10 +3145,10 @@ class DynamicalSystem_projective(SchemeMorphism_polynomial_projective_space, - sage: K.<w> = CyclotomicField(3) - sage: P.<x,y> = ProjectiveSpace(K, 1) - sage: D6 = DynamicalSystem_projective([y^2,x^2]) -- sage: D6.automorphism_group() -+ sage: sorted(D6.automorphism_group()) - [ -- [1 0] [0 w] [0 1] [w 0] [-w - 1 0] [ 0 -w - 1] -- [0 1], [1 0], [1 0], [0 1], [ 0 1], [ 1 0] -+ [-w - 1 0] [ 0 -w - 1] [w 0] [0 w] [0 1] [1 0] -+ [ 0 1], [ 1 0], [0 1], [1 0], [1 0], [0 1] - ] - """ - alg = kwds.get('algorithm', None) -@@ -3748,14 +3748,14 @@ class DynamicalSystem_projective(SchemeMorphism_polynomial_projective_space, - sage: K.<s> = NumberField(w^6 - 3*w^5 + 5*w^4 - 5*w^3 + 5*w^2 - 3*w + 1) - sage: P.<x,y,z> = ProjectiveSpace(K,2) - sage: f = DynamicalSystem_projective([x^2+z^2, y^2+x^2, z^2+y^2]) -- sage: f.preperiodic_points(0,1) -- [(-s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 3*s + 1 : s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 4*s - 1 : 1), -- (-2*s^5 + 4*s^4 - 5*s^3 + 3*s^2 - 4*s : -2*s^5 + 5*s^4 - 7*s^3 + 6*s^2 - 7*s + 3 : 1), -- (-s^5 + 3*s^4 - 4*s^3 + 4*s^2 - 4*s + 2 : -s^5 + 2*s^4 - 2*s^3 + s^2 - s : 1), -- (s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 3*s - 1 : -s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 4*s + 2 : 1), -- (2*s^5 - 6*s^4 + 9*s^3 - 8*s^2 + 7*s - 4 : 2*s^5 - 5*s^4 + 7*s^3 - 5*s^2 + 6*s - 2 : 1), -- (1 : 1 : 1), -- (s^5 - 2*s^4 + 2*s^3 + s : s^5 - 3*s^4 + 4*s^3 - 3*s^2 + 2*s - 1 : 1)] -+ sage: sorted(f.preperiodic_points(0,1), key=str) -+ [(-2*s^5 + 4*s^4 - 5*s^3 + 3*s^2 - 4*s : -2*s^5 + 5*s^4 - 7*s^3 + 6*s^2 - 7*s + 3 : 1), -+ (-s^5 + 3*s^4 - 4*s^3 + 4*s^2 - 4*s + 2 : -s^5 + 2*s^4 - 2*s^3 + s^2 - s : 1), -+ (-s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 3*s + 1 : s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 4*s - 1 : 1), -+ (1 : 1 : 1), -+ (2*s^5 - 6*s^4 + 9*s^3 - 8*s^2 + 7*s - 4 : 2*s^5 - 5*s^4 + 7*s^3 - 5*s^2 + 6*s - 2 : 1), -+ (s^5 - 2*s^4 + 2*s^3 + s : s^5 - 3*s^4 + 4*s^3 - 3*s^2 + 2*s - 1 : 1), -+ (s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 3*s - 1 : -s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 4*s + 2 : 1)] - - :: - -@@ -3969,14 +3969,14 @@ class DynamicalSystem_projective(SchemeMorphism_polynomial_projective_space, - sage: K = NumberField(w^6 - 3*w^5 + 5*w^4 - 5*w^3 + 5*w^2 - 3*w + 1,'s') - sage: P.<x,y,z> = ProjectiveSpace(K,2) - sage: f = DynamicalSystem_projective([x^2+z^2, y^2+x^2, z^2+y^2]) -- sage: f.periodic_points(1) -- [(-s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 3*s + 1 : s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 4*s - 1 : 1), -- (-2*s^5 + 4*s^4 - 5*s^3 + 3*s^2 - 4*s : -2*s^5 + 5*s^4 - 7*s^3 + 6*s^2 - 7*s + 3 : 1), -+ sage: sorted(f.periodic_points(1), key=str) -+ [(-2*s^5 + 4*s^4 - 5*s^3 + 3*s^2 - 4*s : -2*s^5 + 5*s^4 - 7*s^3 + 6*s^2 - 7*s + 3 : 1), - (-s^5 + 3*s^4 - 4*s^3 + 4*s^2 - 4*s + 2 : -s^5 + 2*s^4 - 2*s^3 + s^2 - s : 1), -- (s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 3*s - 1 : -s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 4*s + 2 : 1), -- (2*s^5 - 6*s^4 + 9*s^3 - 8*s^2 + 7*s - 4 : 2*s^5 - 5*s^4 + 7*s^3 - 5*s^2 + 6*s - 2 : 1), -+ (-s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 3*s + 1 : s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 4*s - 1 : 1), - (1 : 1 : 1), -- (s^5 - 2*s^4 + 2*s^3 + s : s^5 - 3*s^4 + 4*s^3 - 3*s^2 + 2*s - 1 : 1)] -+ (2*s^5 - 6*s^4 + 9*s^3 - 8*s^2 + 7*s - 4 : 2*s^5 - 5*s^4 + 7*s^3 - 5*s^2 + 6*s - 2 : 1), -+ (s^5 - 2*s^4 + 2*s^3 + s : s^5 - 3*s^4 + 4*s^3 - 3*s^2 + 2*s - 1 : 1), -+ (s^5 - 2*s^4 + 3*s^3 - 3*s^2 + 3*s - 1 : -s^5 + 3*s^4 - 5*s^3 + 4*s^2 - 4*s + 2 : 1)] - - :: - -@@ -5570,10 +5570,10 @@ class DynamicalSystem_projective_field(DynamicalSystem_projective, - sage: K.<w> = NumberField(x^2-x+1) - sage: P.<u,v> = ProjectiveSpace(K,1) - sage: f = DynamicalSystem_projective([u^2 + v^2,v^2]) -- sage: f.rational_periodic_points() -+ sage: sorted(f.rational_periodic_points()) - doctest:warning - ... -- [(w : 1), (1 : 0), (-w + 1 : 1)] -+ [(-w + 1 : 1), (w : 1), (1 : 0)] - """ - from sage.misc.superseded import deprecation - deprecation(28109, "use sage.dynamics.arithmetic_dynamics.projective_ds.all_periodic_points instead") -@@ -6010,19 +6010,19 @@ class DynamicalSystem_projective_field(DynamicalSystem_projective, - sage: PS.<x,y> = ProjectiveSpace(1,K) - sage: f = DynamicalSystem_projective([x^2 - 29/16*y^2, y^2]) - sage: P = PS([w,1]) -- sage: f.connected_rational_component(P) -- [(w : 1), -- (w^2 - 29/16 : 1), -- (-w^2 - w + 25/16 : 1), -- (w^2 + w - 25/16 : 1), -+ sage: sorted(f.connected_rational_component(P), key=str) -+ [(-w - 1/2 : 1), - (-w : 1), -+ (-w^2 + 21/16 : 1), - (-w^2 + 29/16 : 1), -+ (-w^2 - w + 25/16 : 1), -+ (-w^2 - w + 33/16 : 1), - (w + 1/2 : 1), -- (-w - 1/2 : 1), -- (-w^2 + 21/16 : 1), -- (w^2 - 21/16 : 1), -+ (w : 1), -+ (w^2 + w - 25/16 : 1), - (w^2 + w - 33/16 : 1), -- (-w^2 - w + 33/16 : 1)] -+ (w^2 - 21/16 : 1), -+ (w^2 - 29/16 : 1)] - - :: - -@@ -6144,10 +6144,10 @@ class DynamicalSystem_projective_field(DynamicalSystem_projective, - sage: f = DynamicalSystem_projective([x^2 + y^2, x*y]) - sage: m = matrix(K, 2, 2, [1, 1, 2, 1]) - sage: g = f.conjugate(m) -- sage: f.conjugating_set(g) # long time -+ sage: sorted(f.conjugating_set(g)) # long time - [ -- [1 1] [-1 -1] -- [2 1], [ 2 1] -+ [-1 -1] [1 1] -+ [ 2 1], [2 1] - ] - - :: -diff --git a/src/sage/geometry/cone.py b/src/sage/geometry/cone.py -index d28fa00..be419ef 100644 ---- a/src/sage/geometry/cone.py -+++ b/src/sage/geometry/cone.py -@@ -2279,9 +2279,9 @@ class ConvexRationalPolyhedralCone(IntegralRayCollection, - - sage: face = L.level_sets()[1][0] - sage: D = L.hasse_diagram() -- sage: D.neighbors(face) -- [2-d cone in 2-d lattice N, -- 0-d face of 2-d cone in 2-d lattice N] -+ sage: sorted(D.neighbors(face)) -+ [0-d face of 2-d cone in 2-d lattice N, -+ 2-d cone in 2-d lattice N] - - However, you can achieve some of this functionality using - :meth:`facets`, :meth:`facet_of`, and :meth:`adjacent` methods:: -@@ -4056,11 +4056,11 @@ class ConvexRationalPolyhedralCone(IntegralRayCollection, - The cone need not be strictly convex:: - - sage: halfplane = Cone([(1,0),(2,1),(-1,0)]) -- sage: halfplane.semigroup_generators() -- (N(0, 1), N(1, 0), N(-1, 0)) -+ sage: sorted(halfplane.semigroup_generators()) -+ [N(-1, 0), N(0, 1), N(1, 0)] - sage: line = Cone([(1,1,1),(-1,-1,-1)]) -- sage: line.semigroup_generators() -- (N(1, 1, 1), N(-1, -1, -1)) -+ sage: sorted(line.semigroup_generators()) -+ [N(-1, -1, -1), N(1, 1, 1)] - sage: wedge = Cone([ (1,0,0), (1,2,0), (0,0,1), (0,0,-1) ]) - sage: sorted(wedge.semigroup_generators()) - [N(0, 0, -1), N(0, 0, 1), N(1, 0, 0), N(1, 1, 0), N(1, 2, 0)] -diff --git a/src/sage/geometry/fan.py b/src/sage/geometry/fan.py -index 07acaae..d48310e 100644 ---- a/src/sage/geometry/fan.py -+++ b/src/sage/geometry/fan.py -@@ -532,7 +532,7 @@ def Fan(cones, rays=None, lattice=None, check=True, normalize=True, - "if rays are given, they must include all rays of the fan!") - rays = new_rays - else: -- rays = tuple(ray_set) -+ rays = tuple(sorted(ray_set)) - if check: - # Maybe we should compute all faces of all cones and save them for - # later if we are doing this check? -@@ -1151,7 +1151,7 @@ class RationalPolyhedralFan(IntegralRayCollection, - - sage: fan = Fan([Cone([(1,0), (1,1)]), Cone([(-1,-1)])]) - sage: sage_input(fan) -- Fan(cones=[[0, 1], [2]], rays=[(1, 0), (1, 1), (-1, -1)]) -+ Fan(cones=[[1, 2], [0]], rays=[(-1, -1), (1, 0), (1, 1)]) - """ - cones = [[ZZ(_) for _ in c.ambient_ray_indices()] for c in self.generating_cones()] - rays = [sib(tuple(r)) for r in self.rays()] -@@ -1345,13 +1345,13 @@ class RationalPolyhedralFan(IntegralRayCollection, - sage: cone2 = Cone([(-1,0)]) - sage: fan = Fan([cone1, cone2]) - sage: fan.rays() -+ N(-1, 0), - N( 0, 1), -- N( 1, 0), -- N(-1, 0) -+ N( 1, 0) - in 2-d lattice N - sage: for cone in fan: print(cone.ambient_ray_indices()) -- (0, 1) -- (2,) -+ (1, 2) -+ (0,) - sage: L = fan.cone_lattice() # indirect doctest - sage: L - Finite poset containing 6 elements with distinguished linear extension -@@ -1878,8 +1878,8 @@ class RationalPolyhedralFan(IntegralRayCollection, - sage: cone2 = Cone([(1,0), (0,1)]) - sage: f = Fan([cone1, cone2]) - sage: f.rays() -- N(0, 1), - N(0, -1), -+ N(0, 1), - N(1, 0) - in 2-d lattice N - sage: f.cone_containing(0) # ray index -@@ -2004,13 +2004,13 @@ class RationalPolyhedralFan(IntegralRayCollection, - sage: cone2 = Cone([(-1,0)]) - sage: fan = Fan([cone1, cone2]) - sage: fan.rays() -+ N(-1, 0), - N( 0, 1), -- N( 1, 0), -- N(-1, 0) -+ N( 1, 0) - in 2-d lattice N - sage: for cone in fan: print(cone.ambient_ray_indices()) -- (0, 1) -- (2,) -+ (1, 2) -+ (0,) - sage: L = fan.cone_lattice() - sage: L - Finite poset containing 6 elements with distinguished linear extension -@@ -2034,7 +2034,7 @@ class RationalPolyhedralFan(IntegralRayCollection, - ....: print([f.ambient_ray_indices() for f in l]) - [()] - [(0,), (1,), (2,)] -- [(0, 1)] -+ [(1, 2)] - - If the fan is complete, its cone lattice is atomic and coatomic and - can (and will!) be computed in a much more efficient way, but the -@@ -2122,9 +2122,9 @@ class RationalPolyhedralFan(IntegralRayCollection, - sage: fan(codim=2) - (0-d cone of Rational polyhedral fan in 2-d lattice N,) - sage: for cone in fan.cones(1): cone.ray(0) -+ N(-1, 0) - N(0, 1) - N(1, 0) -- N(-1, 0) - sage: fan.cones(2) - (2-d cone of Rational polyhedral fan in 2-d lattice N,) - -diff --git a/src/sage/geometry/fan_isomorphism.py b/src/sage/geometry/fan_isomorphism.py -index d5ea13b..04732ab 100644 ---- a/src/sage/geometry/fan_isomorphism.py -+++ b/src/sage/geometry/fan_isomorphism.py -@@ -94,10 +94,12 @@ def fan_isomorphism_generator(fan1, fan2): - ....: Cone([m1*vector([-1,-14]), m1*vector([-100, -5])])]) - sage: fan2 = Fan([Cone([m2*vector([23, 14]), m2*vector([ 3,100])]), - ....: Cone([m2*vector([-1,-14]), m2*vector([-100, -5])])]) -- sage: next(fan_isomorphism_generator(fan1, fan2)) -+ sage: sorted(fan_isomorphism_generator(fan1, fan2)) -+ [ - [18 1 -5] - [ 4 0 -1] - [ 5 0 -1] -+ ] - - sage: m0 = identity_matrix(ZZ, 2) - sage: m1 = matrix([(1, 0), (0, -5), (-3, 4)]) -@@ -110,29 +112,29 @@ def fan_isomorphism_generator(fan1, fan2): - ....: Cone([m1*vector([1,1]), m1*vector([0,1])])]) - sage: fan2 = Fan([Cone([m2*vector([1,0]), m2*vector([1,1])]), - ....: Cone([m2*vector([1,1]), m2*vector([0,1])])]) -- sage: tuple(fan_isomorphism_generator(fan0, fan0)) -- ( -- [1 0] [0 1] -- [0 1], [1 0] -- ) -- sage: tuple(fan_isomorphism_generator(fan1, fan1)) -- ( -- [1 0 0] [ -3 -20 28] -- [0 1 0] [ -1 -4 7] -- [0 0 1], [ -1 -5 8] -- ) -- sage: tuple(fan_isomorphism_generator(fan1, fan2)) -- ( -- [18 1 -5] [ 6 -3 7] -- [ 4 0 -1] [ 1 -1 2] -- [ 5 0 -1], [ 2 -1 2] -- ) -- sage: tuple(fan_isomorphism_generator(fan2, fan1)) -- ( -+ sage: sorted(fan_isomorphism_generator(fan0, fan0)) -+ [ -+ [0 1] [1 0] -+ [1 0], [0 1] -+ ] -+ sage: sorted(fan_isomorphism_generator(fan1, fan1)) -+ [ -+ [ -3 -20 28] [1 0 0] -+ [ -1 -4 7] [0 1 0] -+ [ -1 -5 8], [0 0 1] -+ ] -+ sage: sorted(fan_isomorphism_generator(fan1, fan2)) -+ [ -+ [ 6 -3 7] [18 1 -5] -+ [ 1 -1 2] [ 4 0 -1] -+ [ 2 -1 2], [ 5 0 -1] -+ ] -+ sage: sorted(fan_isomorphism_generator(fan2, fan1)) -+ [ - [ 0 -1 1] [ 0 -1 1] - [ 1 -7 2] [ 2 -2 -5] - [ 0 -5 4], [ 1 0 -3] -- ) -+ ] - """ - if not fan_isomorphic_necessary_conditions(fan1, fan2): - return -diff --git a/src/sage/geometry/fan_morphism.py b/src/sage/geometry/fan_morphism.py -index 56bd442..c851978 100644 ---- a/src/sage/geometry/fan_morphism.py -+++ b/src/sage/geometry/fan_morphism.py -@@ -1061,8 +1061,8 @@ class FanMorphism(FreeModuleMorphism): - N( 1, 0) - in 2-d lattice N - sage: xi.factor()[0].domain_fan().rays() -- N( 1, 0), -- N(-1, 0) -+ N(-1, 0), -+ N( 1, 0) - in Sublattice <N(1, 0)> - - We see that one of the rays of the fan of ``P1`` is mapped to a ray, -@@ -1093,7 +1093,7 @@ class FanMorphism(FreeModuleMorphism): - sage: zeta = prod(zeta.factor()[1:]) - sage: Sigma_p = zeta.codomain_fan() - sage: [zeta.index(cone) for cone in flatten(Sigma_p.cones())] -- [4, 4, 1, 4, 4, 4, 4, 1, 1, 1, 1, 1, 1] -+ [4, 4, 4, 1, 4, 4, 4, 1, 1, 1, 1, 1, 1] - sage: zeta.index() == zeta.index(Sigma_p(0)[0]) - True - """ -@@ -1820,9 +1820,9 @@ class FanMorphism(FreeModuleMorphism): - Domain fan: Rational polyhedral fan in Sublattice <N(1, 0, 0), N(0, 1, 0)> - Codomain fan: Rational polyhedral fan in Sublattice <N(1, 0, 0), N(0, 1, 0)> - sage: phi_b.codomain_fan().rays() -- N( 1, 0, 0), -+ N(-1, -1, 0), - N( 0, 1, 0), -- N(-1, -1, 0) -+ N( 1, 0, 0) - in Sublattice <N(1, 0, 0), N(0, 1, 0)> - - Coordinate plane inclusion (injective):: -diff --git a/src/sage/geometry/lattice_polytope.py b/src/sage/geometry/lattice_polytope.py -index 1b7310e..7288b18 100644 ---- a/src/sage/geometry/lattice_polytope.py -+++ b/src/sage/geometry/lattice_polytope.py -@@ -1919,10 +1919,10 @@ class LatticePolytopeClass(SageObject, collections.Hashable): - - sage: face = L.level_sets()[1][0] - sage: D = L.hasse_diagram() -- sage: D.neighbors(face) -- [1-d face of 2-d lattice polytope in 2-d lattice M, -+ sage: sorted(D.neighbors(face)) -+ [-1-d face of 2-d lattice polytope in 2-d lattice M, - 1-d face of 2-d lattice polytope in 2-d lattice M, -- -1-d face of 2-d lattice polytope in 2-d lattice M] -+ 1-d face of 2-d lattice polytope in 2-d lattice M] - - However, you can achieve some of this functionality using - :meth:`facets`, :meth:`facet_of`, and :meth:`adjacent` methods:: -@@ -3981,7 +3981,7 @@ class LatticePolytopeClass(SageObject, collections.Hashable): - raise ValueError("Boundary can be traversed only for 2-polytopes!") - zero_faces = set(self.faces(0)) - l = [self.faces(0)[0]] -- prev, next = zero_faces.intersection(l[0].adjacent()) -+ prev, next = sorted(zero_faces.intersection(l[0].adjacent())) - l = [prev, l[0], next] - while len(l) < self.nvertices(): - prev, next = zero_faces.intersection(l[-1].adjacent()) -diff --git a/src/sage/geometry/linear_expression.py b/src/sage/geometry/linear_expression.py -index 43b2f21..be20596 100644 ---- a/src/sage/geometry/linear_expression.py -+++ b/src/sage/geometry/linear_expression.py -@@ -383,9 +383,8 @@ class LinearExpression(ModuleElement): - - sage: from sage.geometry.linear_expression import LinearExpressionModule - sage: L.<x> = LinearExpressionModule(QQ) -- sage: hash(L([0,1])) -- 3430019387558 # 64-bit -- -1659481946 # 32-bit -+ sage: hash(L([0,1])) == hash((1,)) -+ True - """ - return hash(self._coeffs) ^ hash(self._const) - -diff --git a/src/sage/geometry/polyhedron/combinatorial_polyhedron/base.pyx b/src/sage/geometry/polyhedron/combinatorial_polyhedron/base.pyx -index 24aea47..fbd84fb 100644 ---- a/src/sage/geometry/polyhedron/combinatorial_polyhedron/base.pyx -+++ b/src/sage/geometry/polyhedron/combinatorial_polyhedron/base.pyx -@@ -1502,10 +1502,10 @@ cdef class CombinatorialPolyhedron(SageObject): - A vertex at (0, 1, -1), - A vertex at (0, 1, 1), - A vertex at (1, 0, 0)) -- sage: G.neighbors_out(C.Vrepresentation()[4]) -- [An inequality (-1, 0, -1) x + 1 >= 0, -+ sage: sorted(G.neighbors_out(C.Vrepresentation()[4])) -+ [An inequality (-1, -1, 0) x + 1 >= 0, -+ An inequality (-1, 0, -1) x + 1 >= 0, - An inequality (-1, 0, 1) x + 1 >= 0, -- An inequality (-1, -1, 0) x + 1 >= 0, - An inequality (-1, 1, 0) x + 1 >= 0] - - If ``names`` is ``True`` (the default) but the combinatorial polyhedron -diff --git a/src/sage/geometry/polyhedron/library.py b/src/sage/geometry/polyhedron/library.py -index b0d2a1e..40cbd79 100644 ---- a/src/sage/geometry/polyhedron/library.py -+++ b/src/sage/geometry/polyhedron/library.py -@@ -2637,13 +2637,23 @@ class Polytopes(): - an exact embedded NumberField:: - - sage: perm_a2_reg = polytopes.generalized_permutahedron(['A',2],regular=True) -- sage: perm_a2_reg.vertices() -- (A vertex at (-1/2, -0.866025403784439?), -- A vertex at (-1, 0), -+ sage: V = sorted(perm_a2_reg.vertices()); V # random -+ [A vertex at (-1, 0), -+ A vertex at (-1/2, -0.866025403784439?), -+ A vertex at (-1/2, 0.866025403784439?), - A vertex at (1/2, -0.866025403784439?), -+ A vertex at (1/2, 0.866025403784439?), -+ A vertex at (1.000000000000000?, 0.?e-18)] -+ sage: for v in V: -+ ....: for x in v: -+ ....: x.exactify() -+ sage: V -+ [A vertex at (-1, 0), -+ A vertex at (-1/2, -0.866025403784439?), - A vertex at (-1/2, 0.866025403784439?), -- A vertex at (1.000000000000000?, 0.?e-18), -- A vertex at (0.500000000000000?, 0.866025403784439?)) -+ A vertex at (1/2, -0.866025403784439?), -+ A vertex at (1/2, 0.866025403784439?), -+ A vertex at (1, 0)] - sage: perm_a2_reg.is_inscribed() - True - sage: perm_a3_reg = polytopes.generalized_permutahedron(['A',3],regular=True) # long time -@@ -2653,22 +2663,22 @@ class Polytopes(): - The same is possible with vertices in ``RDF``:: - - sage: perm_a2_inexact = polytopes.generalized_permutahedron(['A',2],exact=False) -- sage: perm_a2_inexact.vertices() -- (A vertex at (0.0, 1.0), -+ sage: sorted(perm_a2_inexact.vertices()) -+ [A vertex at (-1.0, -1.0), - A vertex at (-1.0, 0.0), -- A vertex at (-1.0, -1.0), - A vertex at (0.0, -1.0), -+ A vertex at (0.0, 1.0), - A vertex at (1.0, 0.0), -- A vertex at (1.0, 1.0)) -+ A vertex at (1.0, 1.0)] - - sage: perm_a2_inexact_reg = polytopes.generalized_permutahedron(['A',2],exact=False,regular=True) -- sage: perm_a2_inexact_reg.vertices() -- (A vertex at (-0.5, 0.8660254038), -- A vertex at (-1.0, 0.0), -+ sage: sorted(perm_a2_inexact_reg.vertices()) -+ [A vertex at (-1.0, 0.0), - A vertex at (-0.5, -0.8660254038), -+ A vertex at (-0.5, 0.8660254038), - A vertex at (0.5, -0.8660254038), -- A vertex at (1.0, 0.0), -- A vertex at (0.5, 0.8660254038)) -+ A vertex at (0.5, 0.8660254038), -+ A vertex at (1.0, 0.0)] - - It works also with types with non-rational coordinates:: - -diff --git a/src/sage/geometry/polyhedron/representation.py b/src/sage/geometry/polyhedron/representation.py -index d68682c..7b957ee 100644 ---- a/src/sage/geometry/polyhedron/representation.py -+++ b/src/sage/geometry/polyhedron/representation.py -@@ -90,9 +90,8 @@ class PolyhedronRepresentation(SageObject): - - sage: from sage.geometry.polyhedron.representation import Hrepresentation - sage: pr = Hrepresentation(Polyhedron(vertices = [[1,2,3]]).parent()) -- sage: hash(pr) -- 1647257843 # 32-bit -- 4686581268940269811 # 64-bit -+ sage: hash(pr) == hash(tuple([0,0,0,0])) -+ True - """ - # TODO: ideally the argument self._vector of self should be immutable. - # So that we could change the line below by hash(self._vector). The -diff --git a/src/sage/geometry/triangulation/point_configuration.py b/src/sage/geometry/triangulation/point_configuration.py -index bb39263..c53a9bf 100644 ---- a/src/sage/geometry/triangulation/point_configuration.py -+++ b/src/sage/geometry/triangulation/point_configuration.py -@@ -1397,9 +1397,9 @@ class PointConfiguration(UniqueRepresentation, PointConfiguration_base): - - EXAMPLES:: - -- sage: p = PointConfiguration([(0,0),(+1,0),(-1,0),(0,+1),(0,-1)]) -- sage: list( p.circuits_support() ) -- [(0, 3, 4), (0, 1, 2), (1, 2, 3, 4)] -+ sage: p = PointConfiguration([(0,0), (+1,0), (-1,0), (0,+1), (0,-1)]) -+ sage: sorted(p.circuits_support()) -+ [(0, 1, 2), (0, 3, 4), (1, 2, 3, 4)] - """ - n = len(self) - U = [self[i].reduced_projective() for i in range(n)] -@@ -1468,8 +1468,8 @@ class PointConfiguration(UniqueRepresentation, PointConfiguration_base): - EXAMPLES:: - - sage: p = PointConfiguration([(0,0),(+1,0),(-1,0),(0,+1),(0,-1)]) -- sage: p.circuits() -- (((0,), (1, 2), (3, 4)), ((0,), (3, 4), (1, 2)), ((1, 2), (0,), (3, 4))) -+ sage: sorted(p.circuits()) -+ [((0,), (1, 2), (3, 4)), ((0,), (3, 4), (1, 2)), ((1, 2), (0,), (3, 4))] - - - TESTS:: -@@ -1523,8 +1523,8 @@ class PointConfiguration(UniqueRepresentation, PointConfiguration_base): - EXAMPLES:: - - sage: p = PointConfiguration([(1,0,0),(0,1,0),(0,0,1),(-2,0,-1),(-2,-1,0),(-3,-1,-1),(1,1,1),(-1,0,0),(0,0,0)]) -- sage: p.positive_circuits(8) -- ((0, 7), (0, 1, 4), (0, 2, 3), (0, 5, 6), (0, 1, 2, 5), (0, 3, 4, 6)) -+ sage: sorted(p.positive_circuits(8)) -+ [(0, 1, 2, 5), (0, 1, 4), (0, 2, 3), (0, 3, 4, 6), (0, 5, 6), (0, 7)] - sage: p.positive_circuits(0,5,6) - ((8,),) - """ -diff --git a/src/sage/graphs/generic_graph.py b/src/sage/graphs/generic_graph.py -index d24eb3d..8d97487 100644 ---- a/src/sage/graphs/generic_graph.py -+++ b/src/sage/graphs/generic_graph.py -@@ -5223,25 +5223,25 @@ class GenericGraph(GenericGraph_pyx): - - sage: g = graphs.PathGraph(10) - sage: g.layout(layout='planar', save_pos=True, test=True) -- {0: [3, 2], -- 1: [4, 3], -- 2: [3, 4], -- 3: [4, 4], -- 4: [2, 6], -- 5: [8, 1], -- 6: [1, 7], -- 7: [0, 8], -- 8: [1, 1], -- 9: [1, 0]} -+ {0: [0, 8], -+ 1: [8, 1], -+ 2: [1, 0], -+ 3: [7, 1], -+ 4: [1, 1], -+ 5: [5, 3], -+ 6: [2, 3], -+ 7: [2, 4], -+ 8: [1, 6], -+ 9: [2, 5]} - sage: g = graphs.BalancedTree(3, 4) - sage: pos = g.layout(layout='planar', save_pos=True, test=True) - sage: pos[0] -- [2, 116] -+ [0, 119] - sage: pos[120] -- [3, 64] -+ [21, 37] - sage: g = graphs.CycleGraph(7) - sage: g.layout(layout='planar', save_pos=True, test=True) -- {0: [1, 4], 1: [5, 1], 2: [0, 5], 3: [1, 0], 4: [1, 2], 5: [2, 1], 6: [4, 1]} -+ {0: [0, 5], 1: [5, 1], 2: [1, 0], 3: [4, 1], 4: [1, 1], 5: [2, 2], 6: [1, 2]} - sage: g = graphs.CompleteGraph(5) - sage: g.layout(layout='planar', save_pos=True, test=True, set_embedding=True) - Traceback (most recent call last): -@@ -5860,17 +5860,17 @@ class GenericGraph(GenericGraph_pyx): - sage: T = graphs.TetrahedralGraph() - sage: T.faces({0: [1, 3, 2], 1: [0, 2, 3], 2: [0, 3, 1], 3: [0, 1, 2]}) - [[(0, 1), (1, 2), (2, 0)], -- [(3, 2), (2, 1), (1, 3)], -- [(3, 0), (0, 2), (2, 3)], -- [(3, 1), (1, 0), (0, 3)]] -+ [(0, 2), (2, 3), (3, 0)], -+ [(0, 3), (3, 1), (1, 0)], -+ [(1, 3), (3, 2), (2, 1)]] - - With no embedding provided:: - - sage: graphs.TetrahedralGraph().faces() - [[(0, 1), (1, 2), (2, 0)], -- [(3, 2), (2, 1), (1, 3)], -- [(3, 0), (0, 2), (2, 3)], -- [(3, 1), (1, 0), (0, 3)]] -+ [(0, 2), (2, 3), (3, 0)], -+ [(0, 3), (3, 1), (1, 0)], -+ [(1, 3), (3, 2), (2, 1)]] - - With no embedding provided (non-planar graph):: - -@@ -5916,7 +5916,9 @@ class GenericGraph(GenericGraph_pyx): - - # Storage for face paths - faces = [] -- path = [edgeset.pop()] -+ minedge = min(edgeset) -+ path = [minedge] -+ edgeset.discard(minedge) - - # Trace faces - while edgeset: -@@ -5926,7 +5928,9 @@ class GenericGraph(GenericGraph_pyx): - e = (v, next_node) - if e == path[0]: - faces.append(path) -- path = [edgeset.pop()] -+ minedge = min(edgeset) -+ path = [minedge] -+ edgeset.discard(minedge) - else: - path.append(e) - edgeset.discard(e) -diff --git a/src/sage/graphs/graph.py b/src/sage/graphs/graph.py -index 596c0a38..243e75b 100644 ---- a/src/sage/graphs/graph.py -+++ b/src/sage/graphs/graph.py -@@ -7390,9 +7390,11 @@ class Graph(GenericGraph): - sage: d = F.cliques_containing_vertex() - sage: all(F.degree(u) == len(cliques) for u,cliques in d.items()) - True -- sage: F.cliques_containing_vertex(vertices=[(0, 1)]) -- {(0, 1): [[(0, 1), (0, 0)], [(0, 1), (0, 2)], [(0, 1), (1, 1)]]} -- -+ sage: d = F.cliques_containing_vertex(vertices=[(0, 1)]) -+ sage: list(d) -+ [(0, 1)] -+ sage: sorted(sorted(x for x in L) for L in d[(0, 1)]) -+ [[(0, 0), (0, 1)], [(0, 1), (0, 2)], [(0, 1), (1, 1)]] - """ - import networkx - return networkx.cliques_containing_node(self.networkx_graph(), vertices, cliques) -@@ -7764,8 +7766,11 @@ class Graph(GenericGraph): - - Vertices may be arbitrary --- check that :trac:`24898` is fixed:: - -- sage: Graph({(1,2):[(2,3)],(2,3):[(1,2)]}).modular_decomposition() -- (SERIES, [(1, 2), (2, 3)]) -+ sage: md = Graph({(1,2):[(2,3)],(2,3):[(1,2)]}).modular_decomposition() -+ sage: md[0] -+ SERIES -+ sage: sorted(md[1]) -+ [(1, 2), (2, 3)] - - Unknown algorithm:: - -diff --git a/src/sage/graphs/graph_latex.py b/src/sage/graphs/graph_latex.py -index a9b75e8..8fe69f4 100644 ---- a/src/sage/graphs/graph_latex.py -+++ b/src/sage/graphs/graph_latex.py -@@ -1156,7 +1156,7 @@ class GraphLatex(SageObject): - # - elif name in color_dicts: - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, c in value.items(): - try: -@@ -1165,42 +1165,42 @@ class GraphLatex(SageObject): - raise ValueError('%s option for %s needs to be a matplotlib color (always as a string), not %s' % (name, key, c)) - elif name in positive_scalar_dicts: - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, x in value.items(): - if not type(x) in [int, Integer, float, RealLiteral] or not x >= 0.0: - raise ValueError('%s option for %s needs to be a positive number, not %s' % (name, key, x)) - elif name in boolean_dicts: - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, b in value.items(): - if not isinstance(b, bool): - raise ValueError('%s option for %s needs to be True or False, not %s' % (name, key, b)) - elif name == 'vertex_shapes': - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, s in value.items(): - if s not in shape_names: - raise ValueError('%s option for %s needs to be a vertex shape, not %s' % (name, key, s)) - elif name == 'vertex_label_placements': - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, p in value.items(): - if not(p == 'center') and not(isinstance(p, tuple) and len(p) == 2 and type(p[0]) in number_types and p[0] >= 0 and type(p[1]) in number_types and p[1] >= 0): - raise ValueError('%s option for %s needs to be None or a pair of positive numbers, not %s' % (name, key, p)) - elif name == 'edge_label_placements': - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, p in value.items(): - if not(type(p) in [float, RealLiteral] and (0 <= p) and (p <= 1)) and not(p in label_places): - raise ValueError('%s option for %s needs to be a number between 0.0 and 1.0 or a place (like "above"), not %s' % (name, key, p)) - elif name == 'loop_placements': - if not isinstance(value, dict): -- raise TypeError('%s option must be a dictionary, not %s' (name, value)) -+ raise TypeError('%s option must be a dictionary, not %s' % (name, value)) - else: - for key, p in value.items(): - if not((isinstance(p, tuple)) and (len(p) == 2) and (p[0] >= 0) and (p[1] in compass_points)): -diff --git a/src/sage/graphs/schnyder.py b/src/sage/graphs/schnyder.py -index 879cd0e..21d3c2b 100644 ---- a/src/sage/graphs/schnyder.py -+++ b/src/sage/graphs/schnyder.py -@@ -177,7 +177,7 @@ def _normal_label(g, comb_emb, external_face): - True - sage: faces = g.faces(g._embedding) - sage: _triangulate(g, g._embedding) -- [(2, 0), (4, 2), (6, 4), (1, 3), (6, 1), (3, 5), (4, 0), (6, 3)] -+ [(2, 0), (4, 2), (6, 4), (5, 0), (3, 5), (1, 3), (4, 0), (3, 0)] - sage: tn = _normal_label(g, g._embedding, faces[0]) - sage: _realizer(g, tn) - ({0: [<sage.graphs.schnyder.TreeNode object at ...>]}, -@@ -401,7 +401,7 @@ def _realizer(g, x, example=False): - True - sage: faces = g.faces(g._embedding) - sage: _triangulate(g, g._embedding) -- [(2, 0), (4, 2), (6, 4), (1, 3), (6, 1), (3, 5), (4, 0), (6, 3)] -+ [(2, 0), (4, 2), (6, 4), (5, 0), (3, 5), (1, 3), (4, 0), (3, 0)] - sage: tn = _normal_label(g, g._embedding, faces[0]) - sage: _realizer(g, tn) - ({0: [<sage.graphs.schnyder.TreeNode object at ...>]}, -@@ -488,12 +488,12 @@ def _compute_coordinates(g, x): - True - sage: faces = g.faces(g._embedding) - sage: _triangulate(g, g._embedding) -- [(2, 0), (4, 2), (6, 4), (1, 3), (6, 1), (3, 5), (4, 0), (6, 3)] -+ [(2, 0), (4, 2), (6, 4), (5, 0), (3, 5), (1, 3), (4, 0), (3, 0)] - sage: tn = _normal_label(g, g._embedding, faces[0]) - sage: r = _realizer(g, tn) - sage: _compute_coordinates(g,r) - sage: g.get_pos() -- {0: [0, 5], 1: [5, 1], 2: [1, 0], 3: [4, 1], 4: [1, 1], 5: [2, 2], 6: [1, 4]} -+ {0: [0, 5], 1: [5, 1], 2: [1, 0], 3: [4, 1], 4: [1, 1], 5: [2, 2], 6: [1, 2]} - """ - - tree_nodes, (v1, v2, v3) = x -diff --git a/src/sage/groups/free_group.py b/src/sage/groups/free_group.py -index 198e17b..743bf66 100644 ---- a/src/sage/groups/free_group.py -+++ b/src/sage/groups/free_group.py -@@ -235,9 +235,8 @@ class FreeGroupElement(ElementLibGAP): - TESTS:: - - sage: G.<a,b> = FreeGroup() -- sage: hash(a*b*b*~a) -- -485698212495963022 # 64-bit -- -1876767630 # 32-bit -+ sage: hash(a*b*b*~a) == hash((1, 2, 2, -1)) -+ True - """ - return hash(self.Tietze()) - -diff --git a/src/sage/homology/cubical_complex.py b/src/sage/homology/cubical_complex.py -index 6871c9a..7acb008 100644 ---- a/src/sage/homology/cubical_complex.py -+++ b/src/sage/homology/cubical_complex.py -@@ -699,9 +699,8 @@ class Cube(SageObject): - - sage: from sage.homology.cubical_complex import Cube - sage: C1 = Cube([[1,1], [2,3], [4,5]]) -- sage: C1.__hash__() -- 837272820736660832 # 64-bit -- -1004989088 # 32-bit -+ sage: hash(C1) == hash(((1,1),(2,3),(4,5))) -+ True - """ - return hash(self.__tuple) - -diff --git a/src/sage/homology/homology_vector_space_with_basis.py b/src/sage/homology/homology_vector_space_with_basis.py -index e88fa9e..727d562 100644 ---- a/src/sage/homology/homology_vector_space_with_basis.py -+++ b/src/sage/homology/homology_vector_space_with_basis.py -@@ -107,19 +107,19 @@ class HomologyVectorSpaceWithBasis(CombinatorialFreeModule): - This works with simplicial, cubical, and `\Delta`-complexes, and - also simplicial sets:: - -- sage: Klein_c = cubical_complexes.KleinBottle() -- sage: H = Klein_c.cohomology_ring(GF(2)) -+ sage: Torus_c = cubical_complexes.Torus() -+ sage: H = Torus_c.cohomology_ring(GF(2)) - sage: x,y = H.basis(1) - sage: x.cup_product(x) - 0 - sage: x.cup_product(y) - h^{2,0} - sage: y.cup_product(y) -- h^{2,0} -+ 0 - - sage: Klein_d = delta_complexes.KleinBottle() - sage: H = Klein_d.cohomology_ring(GF(2)) -- sage: u,v = H.basis(1) -+ sage: u,v = sorted(H.basis(1)) - sage: u.cup_product(u) - h^{2,0} - sage: u.cup_product(v) -diff --git a/src/sage/homology/simplicial_complex_morphism.py b/src/sage/homology/simplicial_complex_morphism.py -index 65983bc..8db933b 100644 ---- a/src/sage/homology/simplicial_complex_morphism.py -+++ b/src/sage/homology/simplicial_complex_morphism.py -@@ -81,7 +81,7 @@ EXAMPLES:: - sage: z = y.fiber_product(x) - sage: z # this is the mapping path space - Simplicial complex morphism: -- From: Simplicial complex with 6 vertices and 4 facets -+ From: Simplicial complex with 6 vertices and ... facets - To: Minimal triangulation of the 2-sphere - Defn: ['L0R(0, 0)', 'L0R(0, 1)', 'L1R(1, 0)', 'L1R(1, 1)', 'L2R(2, 0)', 'L2R(2, 1)'] --> [0, 0, 1, 1, 2, 2] - """ -diff --git a/src/sage/interacts/debugger.py b/src/sage/interacts/debugger.py -index e8aa9f6..4ec9287 100644 ---- a/src/sage/interacts/debugger.py -+++ b/src/sage/interacts/debugger.py -@@ -211,8 +211,8 @@ class Debug(object): - else: - file = filename - -- import cgi -- t = """%s<hr>> %s"""%(cgi.escape(code), file) -+ import html -+ t = """%s<hr>> %s"""%(html.escape(code), file) - return t - - def interact(self): -diff --git a/src/sage/interfaces/gap.py b/src/sage/interfaces/gap.py -index 5f24b10..123afb8 100644 ---- a/src/sage/interfaces/gap.py -+++ b/src/sage/interfaces/gap.py -@@ -1577,7 +1577,7 @@ def gap_reset_workspace(max_workspace_size=None, verbose=False): - sage: P = [Process(target=gap, args=("14242",)) for i in range(4)] - sage: for p in P: # long time, indirect doctest - ....: p.start() -- ....: time.sleep(0.2) -+ ....: time.sleep(float(0.2)) - sage: for p in P: # long time - ....: p.join() - sage: os.unlink(sage.interfaces.gap.WORKSPACE) # long time -diff --git a/src/sage/interfaces/process.pyx b/src/sage/interfaces/process.pyx -index d4cf54e..ace308a 100644 ---- a/src/sage/interfaces/process.pyx -+++ b/src/sage/interfaces/process.pyx -@@ -127,7 +127,7 @@ cdef class ContainChildren(object): - ....: _ = sys.stdout.write("X ") - ....: with ContainChildren(): - ....: _ = sys.stdout.write("Y ") -- ....: sleep(0.5) # Give the child process time -+ ....: sleep(float(0.5)) # Give the child process time - ....: print("Z") - ....: finally: - ....: pass -diff --git a/src/sage/interfaces/sagespawn.pyx b/src/sage/interfaces/sagespawn.pyx -index 8644b08..9041238 100644 ---- a/src/sage/interfaces/sagespawn.pyx -+++ b/src/sage/interfaces/sagespawn.pyx -@@ -94,7 +94,7 @@ class SageSpawn(spawn): - sage: s # indirect doctest - stupid process with PID ... running .../true - sage: while s.isalive(): # Wait until the process finishes -- ....: sleep(0.1) -+ ....: sleep(float(0.1)) - sage: s # indirect doctest - stupid process finished running .../true - """ -@@ -188,7 +188,7 @@ class SagePtyProcess(PtyProcess): - sage: s = SageSpawn("sleep 1000") - sage: s.close() - sage: while s.isalive(): # long time (5 seconds) -- ....: sleep(0.1) -+ ....: sleep(float(0.1)) - """ - if not self.closed: - if self.quit_string is not None: -@@ -233,7 +233,7 @@ class SagePtyProcess(PtyProcess): - ....: try: - ....: os.kill(s.pid, 0) - ....: except OSError: -- ....: sleep(0.1) -+ ....: sleep(float(0.1)) - ....: else: - ....: break # process got killed - """ -diff --git a/src/sage/matroids/graphic_matroid.py b/src/sage/matroids/graphic_matroid.py -index 067753f..5f561ff 100644 ---- a/src/sage/matroids/graphic_matroid.py -+++ b/src/sage/matroids/graphic_matroid.py -@@ -1656,7 +1656,7 @@ class GraphicMatroid(Matroid): - - sage: N = Matroid(range(4), graphs.CycleGraph(4)) - sage: I = N.graphic_coextensions(element='a') -- sage: for N1 in I: -+ sage: for N1 in I: # random - ....: N1.graph().edges(sort=True) - [(0, 1, 0), (0, 3, 1), (0, 4, 'a'), (1, 2, 2), (2, 3, 3)] - [(0, 1, 0), (0, 3, 1), (1, 4, 2), (2, 3, 3), (2, 4, 'a')] -diff --git a/src/sage/matroids/linear_matroid.pyx b/src/sage/matroids/linear_matroid.pyx -index bf354d8..ed80897 100644 ---- a/src/sage/matroids/linear_matroid.pyx -+++ b/src/sage/matroids/linear_matroid.pyx -@@ -3671,10 +3671,12 @@ cdef class BinaryMatroid(LinearMatroid): - sage: M = matroids.named_matroids.R12() - sage: N = BinaryMatroid(reduced_matrix=M.representation(reduced=True, - ....: labels=False), groundset='abcdefghijkl') -- sage: N._projection_partition() -+ sage: Npp = N._projection_partition(); Npp # random - 2 x 12 BinaryMatrix - [110011001100] - [001100110011] -+ sage: sorted(Npp._matrix_().rows()) -+ [(1, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0, 0), (0, 0, 1, 1, 0, 0, 1, 1, 0, 0, 1, 1)] - """ - if self._eq_part is None: - if self._b_invariant is None: -diff --git a/src/sage/misc/fpickle.pyx b/src/sage/misc/fpickle.pyx -index 0305532..502080e 100644 ---- a/src/sage/misc/fpickle.pyx -+++ b/src/sage/misc/fpickle.pyx -@@ -8,6 +8,7 @@ REFERENCE: The python cookbook. - - import copyreg - import pickle -+import sys - import types - - -@@ -37,7 +38,10 @@ def reduce_code(co): - if co.co_freevars or co.co_cellvars: - raise ValueError("Cannot pickle code objects from closures") - -- co_args = (co.co_argcount, co.co_kwonlyargcount, co.co_nlocals, -+ co_args = (co.co_argcount,) -+ if sys.version_info.minor >= 8: -+ co_args += (co.co_posonlyargcount,) -+ co_args += (co.co_kwonlyargcount, co.co_nlocals, - co.co_stacksize, co.co_flags, co.co_code, - co.co_consts, co.co_names, co.co_varnames, co.co_filename, - co.co_name, co.co_firstlineno, co.co_lnotab) -diff --git a/src/sage/misc/sage_eval.py b/src/sage/misc/sage_eval.py -index 63fa92b..ca1eb9d 100644 ---- a/src/sage/misc/sage_eval.py -+++ b/src/sage/misc/sage_eval.py -@@ -162,7 +162,7 @@ def sage_eval(source, locals=None, cmds='', preparse=True): - File "<string>", line 1 - RR(Integer(22)/Integer(7)] - ^ -- SyntaxError: unexpected EOF while parsing -+ SyntaxError: ... - - :: - -diff --git a/src/sage/misc/sageinspect.py b/src/sage/misc/sageinspect.py -index d328237..5a11820 100644 ---- a/src/sage/misc/sageinspect.py -+++ b/src/sage/misc/sageinspect.py -@@ -427,8 +427,9 @@ class SageArgSpecVisitor(ast.NodeVisitor): - [(37.0, 'temp'), ('a', ('e', 2, [None, ({False: True}, 'pi')]))] - sage: v = ast.parse("jc = ['veni', 'vidi', 'vici']").body[0]; v - <_ast.Assign object at ...> -- sage: [x for x in dir(v) if not x.startswith('__')] -- ['_attributes', '_fields', 'col_offset', 'lineno', 'targets', 'value'] -+ sage: attrs = [x for x in dir(v) if not x.startswith('__')] -+ sage: '_attributes' in attrs and '_fields' in attrs and 'col_offset' in attrs -+ True - sage: visitor.visit(v.targets[0]) - 'jc' - sage: visitor.visit(v.value) -diff --git a/src/sage/modular/btquotients/btquotient.py b/src/sage/modular/btquotients/btquotient.py -index 2ab15f9..f0b9e43 100644 ---- a/src/sage/modular/btquotients/btquotient.py -+++ b/src/sage/modular/btquotients/btquotient.py -@@ -1522,9 +1522,10 @@ class BruhatTitsQuotient(SageObject, UniqueRepresentation): - EXAMPLES:: - - sage: X = BruhatTitsQuotient(5,13) -- sage: X._cache_key() -- -406423199 # 32-bit -- 1375458358400022881 # 64-bit -+ sage: X._cache_key() == BruhatTitsQuotient(5,13)._cache_key() -+ True -+ sage: X._cache_key() == BruhatTitsQuotient(5,11)._cache_key() -+ False - - sage: Y = BruhatTitsQuotient(5,13,use_magma = True) # optional - magma - sage: Y._cache_key() == X._cache_key() # optional - magma -diff --git a/src/sage/modular/cusps.py b/src/sage/modular/cusps.py -index 9727adf..f468d42 100644 ---- a/src/sage/modular/cusps.py -+++ b/src/sage/modular/cusps.py -@@ -238,12 +238,10 @@ class Cusp(Element): - """ - EXAMPLES:: - -- sage: hash(Cusp(1/3)) -- 1298787075 # 32-bit -- 3713081631933328131 # 64-bit -- sage: hash(Cusp(oo)) -- 1302034650 # 32-bit -- 3713081631936575706 # 64-bit -+ sage: hash(Cusp(1/3)) == hash((1,3)) -+ True -+ sage: hash(Cusp(oo)) == hash((1,0)) -+ True - """ - return hash((self.__a, self.__b)) - -diff --git a/src/sage/modular/dirichlet.py b/src/sage/modular/dirichlet.py -index 0313f30..ac970f5 100644 ---- a/src/sage/modular/dirichlet.py -+++ b/src/sage/modular/dirichlet.py -@@ -416,9 +416,8 @@ class DirichletCharacter(MultiplicativeGroupElement): - EXAMPLES:: - - sage: e = DirichletGroup(16)([-1, 1]) -- sage: hash(e) -- -1497246046 # 32-bit -- -3713082714463545694 # 64-bit -+ sage: hash(e) == hash((-1,1)) -+ True - """ - return hash(self.values_on_gens()) - -diff --git a/src/sage/modular/modform_hecketriangle/hecke_triangle_groups.py b/src/sage/modular/modform_hecketriangle/hecke_triangle_groups.py -index 5c333a2..cb336f6 100644 ---- a/src/sage/modular/modform_hecketriangle/hecke_triangle_groups.py -+++ b/src/sage/modular/modform_hecketriangle/hecke_triangle_groups.py -@@ -918,23 +918,23 @@ class HeckeTriangleGroup(FinitelyGeneratedMatrixGroup_generic, - sage: [key for key in sorted(G._conj_prim)] - [-4, lam - 3, 0, 4*lam, 7*lam + 6, 9*lam + 5, 15*lam + 6, 33*lam + 21] - sage: for key in sorted(G._conj_prim): -- ....: print(G._conj_prim[key]) -+ ....: print(sorted(G._conj_prim[key])) - [[S], [S]] - [[U], [U]] - [[V(4)]] - [[V(3)], [V(2)]] - [[V(1)*V(4)]] - [[V(3)*V(4)], [V(1)*V(2)]] -- [[V(1)*V(3)], [V(2)*V(4)]] -+ [[V(2)*V(4)], [V(1)*V(3)]] - [[V(2)*V(3)]] - sage: [key for key in sorted(G._conj_nonprim)] - [-lam - 2, lam - 3, 32*lam + 16] - - sage: for key in sorted(G._conj_nonprim): -- ....: print(G._conj_nonprim[key]) -- [[U^(-2)], [U^2], [U^(-2)], [U^2]] -+ ....: print(sorted(G._conj_nonprim[key])) -+ [[U^(-2)], [U^(-2)], [U^2], [U^2]] - [[U^(-1)], [U^(-1)]] -- [[V(2)^2], [V(3)^2]] -+ [[V(3)^2], [V(2)^2]] - - sage: G.element_repr_method("default") - """ -@@ -1096,19 +1096,19 @@ class HeckeTriangleGroup(FinitelyGeneratedMatrixGroup_generic, - [[U], [U^(-1)]] - - sage: R = G.class_representatives(14) -- sage: R -+ sage: sorted(R) - [[V(2)*V(3)], [V(1)*V(2)]] -- sage: [v.continued_fraction()[1] for v in R] -+ sage: sorted(v.continued_fraction()[1] for v in R) - [(1, 2, 2), (3,)] - - sage: R = G.class_representatives(32) -- sage: R -+ sage: sorted(R) - [[V(3)^2*V(1)], [V(1)^2*V(3)]] -- sage: [v.continued_fraction()[1] for v in R] -+ sage: [v.continued_fraction()[1] for v in sorted(R)] - [(1, 2, 1, 3), (1, 4)] - - sage: R = G.class_representatives(32, primitive=False) -- sage: R -+ sage: sorted(R) - [[V(3)^2*V(1)], [V(1)^2*V(3)], [V(2)^2]] - - sage: G.element_repr_method("default") -@@ -1315,13 +1315,13 @@ class HeckeTriangleGroup(FinitelyGeneratedMatrixGroup_generic, - sage: [v.continued_fraction() for v in R] - [((), (1, 3)), ((), (3, 1))] - sage: R = G.reduced_elements(D=14) -- sage: R -+ sage: sorted(R) - [ -- [ 5*lam -3] [ 5*lam -7] [4*lam -3] [3*lam -1] -- [ 7 -2*lam], [ 3 -2*lam], [ 3 -lam], [ 1 0] -+ [3*lam -1] [4*lam -3] [ 5*lam -7] [ 5*lam -3] -+ [ 1 0], [ 3 -lam], [ 3 -2*lam], [ 7 -2*lam] - ] -- sage: [v.continued_fraction() for v in R] -- [((), (1, 2, 2)), ((), (2, 2, 1)), ((), (2, 1, 2)), ((), (3,))] -+ sage: sorted(v.continued_fraction() for v in R) -+ [((), (1, 2, 2)), ((), (2, 1, 2)), ((), (2, 2, 1)), ((), (3,))] - """ - L = self.class_representatives(D=D, primitive=True) - R = [] -@@ -1342,15 +1342,15 @@ class HeckeTriangleGroup(FinitelyGeneratedMatrixGroup_generic, - - sage: from sage.modular.modform_hecketriangle.hecke_triangle_groups import HeckeTriangleGroup - sage: G = HeckeTriangleGroup(n=4) -- sage: G.simple_elements(D=12) -+ sage: sorted(G.simple_elements(D=12)) - [ -- [ 3 lam] [ 1 lam] -- [lam 1], [lam 3] -+ [ 1 lam] [ 3 lam] -+ [lam 3], [lam 1] - ] -- sage: G.simple_elements(D=14) -+ sage: sorted(G.simple_elements(D=14)) - [ -- [2*lam 1] [ lam 1] [2*lam 3] [ lam 3] -- [ 3 lam], [ 3 2*lam], [ 1 lam], [ 1 2*lam] -+ [ lam 1] [ lam 3] [2*lam 1] [2*lam 3] -+ [ 3 2*lam], [ 1 2*lam], [ 3 lam], [ 1 lam] - ] - """ - L = self.class_representatives(D=D, primitive=True) -@@ -1378,14 +1378,17 @@ class HeckeTriangleGroup(FinitelyGeneratedMatrixGroup_generic, - - sage: from sage.modular.modform_hecketriangle.hecke_triangle_groups import HeckeTriangleGroup - sage: G = HeckeTriangleGroup(n=4) -- sage: G.rational_period_functions(k=4, D=12) -+ sage: sorted(G.rational_period_functions(k=4, D=12)) - [(z^4 - 1)/z^4] -- sage: G.rational_period_functions(k=-2, D=12) -+ sage: sorted(G.rational_period_functions(k=-2, D=12)) - [-z^2 + 1, 4*lam*z^2 - 4*lam] -- sage: G.rational_period_functions(k=2, D=14) -- [(z^2 - 1)/z^2, 1/z, (24*z^6 - 120*z^4 + 120*z^2 - 24)/(9*z^8 - 80*z^6 + 146*z^4 - 80*z^2 + 9), (24*z^6 - 120*z^4 + 120*z^2 - 24)/(9*z^8 - 80*z^6 + 146*z^4 - 80*z^2 + 9)] -- sage: G.rational_period_functions(k=-4, D=14) -- [-z^4 + 1, 16*z^4 - 16, -16*z^4 + 16] -+ sage: sorted(G.rational_period_functions(k=2, D=14)) -+ [(24*z^6 - 120*z^4 + 120*z^2 - 24)/(9*z^8 - 80*z^6 + 146*z^4 - 80*z^2 + 9), -+ (24*z^6 - 120*z^4 + 120*z^2 - 24)/(9*z^8 - 80*z^6 + 146*z^4 - 80*z^2 + 9), -+ 1/z, -+ (z^2 - 1)/z^2] -+ sage: sorted(G.rational_period_functions(k=-4, D=14)) -+ [-16*z^4 + 16, -z^4 + 1, 16*z^4 - 16] - """ - try: - k = ZZ(k) -diff --git a/src/sage/modular/modform_hecketriangle/readme.py b/src/sage/modular/modform_hecketriangle/readme.py -index c5455b3..ed5d111 100644 ---- a/src/sage/modular/modform_hecketriangle/readme.py -+++ b/src/sage/modular/modform_hecketriangle/readme.py -@@ -528,8 +528,8 @@ Hecke triangle groups and elements: - [-4, -2, 0] - sage: G.class_number(68) - 4 -- sage: G.class_representatives(68) -- [S*T^(-2)*S*T^(-1)*S*T, -S*T^(-1)*S*T^2*S*T, S*T^(-5)*S*T^(-1)*S, T*S*T^5] -+ sage: sorted(G.class_representatives(68)) -+ [S*T^(-5)*S*T^(-1)*S, S*T^(-2)*S*T^(-1)*S*T, T*S*T^5, -S*T^(-1)*S*T^2*S*T] - sage: R = G.reduced_elements(68) - sage: all(v.is_reduced() for v in R) # long time - True -@@ -546,7 +546,7 @@ Hecke triangle groups and elements: - [-4, -lam - 2, lam - 3, 0] - sage: G.class_number(9*G.lam() + 5) - 2 -- sage: G.class_representatives(9*G.lam() + 5) -+ sage: sorted(G.class_representatives(9*G.lam() + 5)) - [S*T^(-2)*S*T^(-1)*S, T*S*T^2] - sage: R = G.reduced_elements(9*G.lam() + 5) - sage: all(v.is_reduced() for v in R) # long time -diff --git a/src/sage/modular/modsym/relation_matrix.py b/src/sage/modular/modsym/relation_matrix.py -index bc42022..847171b 100644 ---- a/src/sage/modular/modsym/relation_matrix.py -+++ b/src/sage/modular/modsym/relation_matrix.py -@@ -561,7 +561,7 @@ def sparse_2term_quotient(rels, n, F): - ZERO = F.zero() - coef = [ONE for i in range(n)] - related_to_me = [[] for i in range(n)] -- for v0, v1 in rels: -+ for v0, v1 in sorted(rels): - c0 = coef[v0[0]] * F(v0[1]) - c1 = coef[v1[0]] * F(v1[1]) - -diff --git a/src/sage/modular/overconvergent/weightspace.py b/src/sage/modular/overconvergent/weightspace.py -index f660ba9..6629761 100644 ---- a/src/sage/modular/overconvergent/weightspace.py -+++ b/src/sage/modular/overconvergent/weightspace.py -@@ -574,9 +574,8 @@ class AlgebraicWeight(WeightCharacter): - TESTS:: - - sage: w = pAdicWeightSpace(23)(12, DirichletGroup(23, QQ).0) -- sage: hash(w) -- 2363715643371367891 # 64-bit -- -1456525869 # 32-bit -+ sage: hash(w) == hash((12, 23, (-1,))) -+ True - """ - if self._chi.is_trivial(): - return hash(self._k) -diff --git a/src/sage/modules/fg_pid/fgp_element.py b/src/sage/modules/fg_pid/fgp_element.py -index 41a51a0..53857d3 100644 ---- a/src/sage/modules/fg_pid/fgp_element.py -+++ b/src/sage/modules/fg_pid/fgp_element.py -@@ -346,14 +346,12 @@ class FGP_Element(ModuleElement): - sage: W = V.span([2*V.0+4*V.1, 9*V.0+12*V.1, 4*V.2]) - sage: Q = V/W - sage: x = Q.0 + 3*Q.1 -- sage: hash(x) -- 3713081631933328131 # 64-bit -- 1298787075 # 32-bit -+ sage: hash(x) == hash((1,3)) -+ True - - sage: A = AdditiveAbelianGroup([3]) -- sage: hash(A.an_element()) -- 3430019387558 # 64-bit -- -1659481946 # 32-bit -+ sage: hash(A.an_element()) == hash((1,)) -+ True - """ - return hash(self.vector()) - -diff --git a/src/sage/modules/fg_pid/fgp_module.py b/src/sage/modules/fg_pid/fgp_module.py -index 1208768..b111d7f 100644 ---- a/src/sage/modules/fg_pid/fgp_module.py -+++ b/src/sage/modules/fg_pid/fgp_module.py -@@ -1895,9 +1895,8 @@ class FGP_Module_class(Module): - EXAMPLES:: - - sage: A = (ZZ**2) / span([[4,0],[0,3]], ZZ) -- sage: hash(A) -- 1328975982 # 32-bit -- -7071641102956720018 # 64-bit -+ sage: hash(A) == hash(((2, ZZ), ((4, 0), (0, 3)))) -+ True - """ - return hash((self.V(), self.W())) - -diff --git a/src/sage/modules/filtered_vector_space.py b/src/sage/modules/filtered_vector_space.py -index 221694c..fa67153 100644 ---- a/src/sage/modules/filtered_vector_space.py -+++ b/src/sage/modules/filtered_vector_space.py -@@ -758,7 +758,7 @@ class FilteredVectorSpace_class(FreeModule_ambient_field): - filt = self._filt[1:] - for d, V in filt: - generators.update(V.echelonized_basis()) -- generators = tuple(generators) -+ generators = tuple(sorted(generators)) - - filtration = dict() - for d, V in filt: -diff --git a/src/sage/modules/quotient_module.py b/src/sage/modules/quotient_module.py -index 46d8735..3e447c9 100644 ---- a/src/sage/modules/quotient_module.py -+++ b/src/sage/modules/quotient_module.py -@@ -187,15 +187,8 @@ class FreeModule_ambient_field_quotient(FreeModule_ambient_field): - sage: A = QQ^2; V = A.span_of_basis([[1,0], [1,1]]); W = V.span([V.1, V.0]) - sage: Q = V/W; Q.dimension() - 0 -- sage: hash(Q) -- 954887582 # 32-bit -- -5856620741060301410 # 64-bit -- -- The hash is just got by hashing both `V` and `W`:: -- -- sage: hash((V, W)) -- 954887582 # 32-bit -- -5856620741060301410 # 64-bit -+ sage: hash(Q) == hash((V,W)) -+ True - """ - return self.__hash - -diff --git a/src/sage/monoids/free_monoid_element.py b/src/sage/monoids/free_monoid_element.py -index 549f938..e9c04dc 100644 ---- a/src/sage/monoids/free_monoid_element.py -+++ b/src/sage/monoids/free_monoid_element.py -@@ -88,15 +88,12 @@ class FreeMonoidElement(MonoidElement): - TESTS:: - - sage: R.<x,y> = FreeMonoid(2) -- sage: hash(x) -- 1914282862589934403 # 64-bit -- 139098947 # 32-bit -- sage: hash(y) -- 2996819001369607946 # 64-bit -- 13025034 # 32-bit -- sage: hash(x*y) -- 7114093379175463612 # 64-bit -- 2092317372 # 32-bit -+ sage: hash(x) == hash(((0, 1),)) -+ True -+ sage: hash(y) == hash(((1, 1),)) -+ True -+ sage: hash(x*y) == hash(((0, 1), (1, 1))) -+ True - """ - return hash(tuple(self._element_list)) - -diff --git a/src/sage/monoids/indexed_free_monoid.py b/src/sage/monoids/indexed_free_monoid.py -index 8ee49b1..144a957 100644 ---- a/src/sage/monoids/indexed_free_monoid.py -+++ b/src/sage/monoids/indexed_free_monoid.py -@@ -379,12 +379,10 @@ class IndexedFreeMonoidElement(IndexedMonoidElement): - TESTS:: - - sage: F = FreeMonoid(index_set=tuple('abcde')) -- sage: hash(F ([(1,2),(0,1)]) ) -- 2401565693828035651 # 64-bit -- 1164080195 # 32-bit -- sage: hash(F ([(0,2),(1,1)]) ) -- -3359280905493236379 # 64-bit -- -1890405019 # 32-bit -+ sage: hash(F ([(1,2),(0,1)]) ) == hash(((1, 2), (0, 1))) -+ True -+ sage: hash(F ([(0,2),(1,1)]) ) == hash(((0, 2), (1, 1))) -+ True - """ - return hash(self._monomial) - -diff --git a/src/sage/monoids/trace_monoid.py b/src/sage/monoids/trace_monoid.py -index 6e52c3b..c564278 100644 ---- a/src/sage/monoids/trace_monoid.py -+++ b/src/sage/monoids/trace_monoid.py -@@ -948,6 +948,24 @@ class TraceMonoid(UniqueRepresentation, Monoid_class): - if not ((list(word.value)[-1][0], suffix.value) in self._independence - and list(word.value)[-1][0] > suffix.value)]) - -+ def _sorted_independence(self): -+ r""" -+ Return independence relation over the monoid. -+ -+ OUTPUT: sorted list of sorted commuting generator pairs. -+ -+ EXAMPLES:: -+ -+ sage: from sage.monoids.trace_monoid import TraceMonoid -+ sage: F.<a,b,c> = FreeMonoid() -+ sage: I = frozenset(((a,c), (c,a))) -+ sage: M.<ac,bc,cc> = TraceMonoid(F, I=I) -+ sage: M._sorted_independence() -+ [[a, c]] -+ """ -+ return sorted(sorted(x_y) -+ for x_y in sorted(self.independence())) -+ - def _repr_(self): - r""" - Textual representation of trace monoids. -@@ -963,7 +981,7 @@ class TraceMonoid(UniqueRepresentation, Monoid_class): - return ("Trace monoid on {!s} generators {!s} " - "with independence relation {{{}}}").format(self.ngens(), self.gens(), - ", ".join("{{{}, {}}}".format(x, y) -- for (x, y) in sorted(self.independence()))) -+ for (x, y) in self._sorted_independence())) - - def _latex_(self): - r""" -@@ -980,6 +998,6 @@ class TraceMonoid(UniqueRepresentation, Monoid_class): - repr(self._free_monoid.gens())[1:-1], - ",".join( - "{0!r}{1!r}={1!r}{0!r}".format(v1, v2) -- for v1, v2 in sorted(self.independence()) -+ for v1, v2 in self._sorted_independence() - ) - ) -diff --git a/src/sage/parallel/map_reduce.py b/src/sage/parallel/map_reduce.py -index 715a53a..0945dd9 100644 ---- a/src/sage/parallel/map_reduce.py -+++ b/src/sage/parallel/map_reduce.py -@@ -244,7 +244,7 @@ Here is an example or how to deal with timeout:: - sage: from sage.parallel.map_reduce import (RESetMPExample, AbortError) - sage: EX = RESetMPExample(maxl=100) - sage: try: -- ....: res = EX.run(timeout=0.01) -+ ....: res = EX.run(timeout=float(0.01)) - ....: except AbortError: - ....: print("Computation timeout") - ....: else: -@@ -1126,7 +1126,7 @@ class RESetMapReduce(object): - - sage: from sage.parallel.map_reduce import RESetMapReduce - sage: def children(x): -- ....: sleep(0.5) -+ ....: sleep(float(0.5)) - ....: return [] - sage: S = RESetMapReduce(roots=[1], children=children) - sage: S.setup_workers(2) -@@ -1387,7 +1387,7 @@ class RESetMapReduce(object): - sage: EX = RESetMPExample(maxl=6) - sage: EX.setup_workers(2) - sage: EX.random_worker() -- <RESetMapReduceWorker(RESetMapReduceWorker-..., initial)> -+ <RESetMapReduceWorker...RESetMapReduceWorker-... initial...> - sage: EX.random_worker() in EX._workers - True - -@@ -1434,7 +1434,7 @@ class RESetMapReduce(object): - sage: from sage.parallel.map_reduce import AbortError - sage: EX = RESetMPExample(maxl = 100) - sage: try: -- ....: res = EX.run(timeout=0.01) -+ ....: res = EX.run(timeout=float(0.01)) - ....: except AbortError: - ....: print("Computation timeout") - ....: else: -@@ -1571,7 +1571,7 @@ class RESetMapReduceWorker(mp.Process): - sage: from sage.parallel.map_reduce import RESetMPExample, RESetMapReduceWorker - sage: EX = RESetMPExample() - sage: RESetMapReduceWorker(EX, 200, True) -- <RESetMapReduceWorker(RESetMapReduceWorker-..., initial)> -+ <RESetMapReduceWorker...RESetMapReduceWorker-... initial...> - """ - mp.Process.__init__(self) - self._iproc = iproc -diff --git a/src/sage/rings/finite_rings/element_givaro.pyx b/src/sage/rings/finite_rings/element_givaro.pyx -index aa0b2f2..7a61861 100644 ---- a/src/sage/rings/finite_rings/element_givaro.pyx -+++ b/src/sage/rings/finite_rings/element_givaro.pyx -@@ -1595,7 +1595,7 @@ cdef class FiniteField_givaroElement(FinitePolyExtElement): - b - sage: c is b - True -- sage: copy(5r) is 5r -+ sage: copy(5r) == 5r - True - """ - return self -diff --git a/src/sage/rings/polynomial/multi_polynomial_ideal.py b/src/sage/rings/polynomial/multi_polynomial_ideal.py -index 1a7db4d..f025b3a 100644 ---- a/src/sage/rings/polynomial/multi_polynomial_ideal.py -+++ b/src/sage/rings/polynomial/multi_polynomial_ideal.py -@@ -4162,11 +4162,11 @@ class MPolynomialIdeal( MPolynomialIdeal_singular_repr, \ - sage: I = P * ( x*y*z + z^5, 2*x^2 + y^3 + z^7, 3*z^5 +y ^5 ) - sage: J = Ideal(I.groebner_basis()) - sage: f = sum(P.random_element(terms=2)*f for f in I.gens()) -- sage: f -+ sage: f # random - 1/2*y^2*z^7 - 1/4*y*z^8 + 2*x*z^5 + 95*z^6 + 1/2*y^5 - 1/4*y^4*z + x^2*y^2 + 3/2*x^2*y*z + 95*x*y*z^2 -- sage: f.lift(I.gens()) -+ sage: f.lift(I.gens()) # random - [2*x + 95*z, 1/2*y^2 - 1/4*y*z, 0] -- sage: l = f.lift(J.gens()); l -+ sage: l = f.lift(J.gens()); l # random - [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -1/2*y^2 + 1/4*y*z, 1/2*y^2*z^2 - 1/4*y*z^3 + 2*x + 95*z] - sage: sum(map(mul, zip(l,J.gens()))) == f - True -diff --git a/src/sage/rings/universal_cyclotomic_field.py b/src/sage/rings/universal_cyclotomic_field.py -index 52948e2..d56d74f 100644 ---- a/src/sage/rings/universal_cyclotomic_field.py -+++ b/src/sage/rings/universal_cyclotomic_field.py -@@ -615,9 +615,8 @@ class UniversalCyclotomicFieldElement(FieldElement): - sage: UCF = UniversalCyclotomicField() - sage: hash(UCF.zero()) # indirect doctest - 0 -- sage: hash(UCF.gen(3,2)) -- 313156239 # 32-bit -- 1524600308199219855 # 64-bit -+ sage: hash(UCF.gen(3,2)) == hash((3,0,0,1)) -+ True - - TESTS: - -diff --git a/src/sage/schemes/affine/affine_point.py b/src/sage/schemes/affine/affine_point.py -index c217783..5cfe837 100644 ---- a/src/sage/schemes/affine/affine_point.py -+++ b/src/sage/schemes/affine/affine_point.py -@@ -151,9 +151,8 @@ class SchemeMorphism_point_affine(SchemeMorphism_point): - EXAMPLES:: - - sage: A.<x,y> = AffineSpace(QQ, 2) -- sage: hash(A([1, 1])) -- 1300952125 # 32-bit -- 3713081631935493181 # 64-bit -+ sage: hash(A([1, 1])) == hash((1,1)) -+ True - - :: - -@@ -257,9 +256,8 @@ class SchemeMorphism_point_affine_field(SchemeMorphism_point_affine): - - sage: A.<x,y> = AffineSpace(QQ, 2) - sage: X = A.subscheme(x - y) -- sage: hash(X([1, 1])) -- 1300952125 # 32-bit -- 3713081631935493181 # 64-bit -+ sage: hash(X([1, 1])) == hash((1,1)) -+ True - - :: - -diff --git a/src/sage/schemes/curves/curve.py b/src/sage/schemes/curves/curve.py -index 27f187f..f859901 100644 ---- a/src/sage/schemes/curves/curve.py -+++ b/src/sage/schemes/curves/curve.py -@@ -300,13 +300,13 @@ class Curve_generic(AlgebraicScheme_subscheme): - sage: C = Curve([359/12*x*y^2*z^2 + 2*y*z^4 + 187/12*y^3*z^2 + x*z^4\ - + 67/3*x^2*y*z^2 + 117/4*y^5 + 9*x^5 + 6*x^3*z^2 + 393/4*x*y^4\ - + 145*x^2*y^3 + 115*x^3*y^2 + 49*x^4*y], P) -- sage: C.singular_points(K) -- [(b^6 : -b^6 : 1), -+ sage: sorted(C.singular_points(K), key=str) -+ [(-1/2*b^5 - 1/2*b^3 + 1/2*b - 1 : 1 : 0), -+ (-2/3*b^4 + 1/3 : 0 : 1), - (-b^6 : b^6 : 1), - (1/2*b^5 + 1/2*b^3 - 1/2*b - 1 : 1 : 0), -- (-1/2*b^5 - 1/2*b^3 + 1/2*b - 1 : 1 : 0), - (2/3*b^4 - 1/3 : 0 : 1), -- (-2/3*b^4 + 1/3 : 0 : 1)] -+ (b^6 : -b^6 : 1)] - """ - if F is None: - if not self.base_ring() in Fields(): -diff --git a/src/sage/schemes/elliptic_curves/ell_point.py b/src/sage/schemes/elliptic_curves/ell_point.py -index 9e844e6..e7c3024 100644 ---- a/src/sage/schemes/elliptic_curves/ell_point.py -+++ b/src/sage/schemes/elliptic_curves/ell_point.py -@@ -821,10 +821,10 @@ class EllipticCurvePoint_field(SchemeMorphism_point_abelian_variety_field): - [2, 4, 4, 2, 1, 2, 4, 4] - sage: all(T.is_divisible_by(3) for T in tor) - True -- sage: Set([T for T in tor if T.is_divisible_by(2)]) -- {(0 : 1 : 0), (1 : 0 : 1)} -- sage: Set([2*T for T in tor]) -- {(0 : 1 : 0), (1 : 0 : 1)} -+ sage: sorted(T for T in tor if T.is_divisible_by(2)) -+ [(0 : 1 : 0), (1 : 0 : 1)] -+ sage: sorted(Set([2*T for T in tor])) -+ [(0 : 1 : 0), (1 : 0 : 1)] - """ - # Coerce the input m to an integer - m = Integer(m) -diff --git a/src/sage/schemes/product_projective/homset.py b/src/sage/schemes/product_projective/homset.py -index d4b71c2..7f4e1de 100644 ---- a/src/sage/schemes/product_projective/homset.py -+++ b/src/sage/schemes/product_projective/homset.py -@@ -116,8 +116,8 @@ class SchemeHomset_points_product_projective_spaces_field(SchemeHomset_points_pr - sage: u = QQ['u'].0 - sage: P.<x,y,z,w> = ProductProjectiveSpaces([1,1], NumberField(u^2 - 2, 'v')) - sage: X = P.subscheme([x^2 - y^2, z^2 - 2*w^2]) -- sage: X(P.base_ring()).points() -- [(-1 : 1 , -v : 1), (1 : 1 , v : 1), (1 : 1 , -v : 1), (-1 : 1 , v : 1)] -+ sage: sorted(X(P.base_ring()).points()) -+ [(-1 : 1 , -v : 1), (-1 : 1 , v : 1), (1 : 1 , -v : 1), (1 : 1 , v : 1)] - - :: - -diff --git a/src/sage/schemes/product_projective/point.py b/src/sage/schemes/product_projective/point.py -index c981dcd..fecf560 100644 ---- a/src/sage/schemes/product_projective/point.py -+++ b/src/sage/schemes/product_projective/point.py -@@ -270,26 +270,22 @@ class ProductProjectiveSpaces_point_ring(SchemeMorphism_point): - :: - - sage: PP = ProductProjectiveSpaces(ZZ, [1, 2]) -- sage: hash(PP([1, 1, 2, 2, 2])) -- 805439612 # 32-bit -- 7267864846446758012 # 64-bit -- sage: hash(PP([1, 1, 1, 1, 1])) -- 805439612 # 32-bit -- 7267864846446758012 # 64-bit -+ sage: hash(PP([1, 1, 2, 2, 2])) == hash(PP([1, 1, 1, 1, 1])) -+ True - - :: - - sage: PP = ProductProjectiveSpaces(QQ, [1, 1]) -- sage: hash(PP([1/7, 1, 2, 1])) -- 1139616004 # 32-bit -- -7585172175017137916 # 64-bit -+ sage: hash(PP([1/7, 1, 2, 1])) == hash((1/7, 1, 2, 1)) -+ True - - :: - - sage: PP = ProductProjectiveSpaces(GF(7), [1, 1, 1]) -- sage: hash(PP([4, 1, 5, 4, 6, 1])) -- 1796924635 # 32-bit -- -4539377540667874085 # 64-bit -+ sage: hash(PP([4, 1, 5, 4, 6, 1])) == hash((4, 1, 5, 4, 6, 1)) -+ False -+ sage: hash(PP([4, 1, 5, 4, 6, 1])) == hash((4, 1, 3, 1, 6, 1)) -+ True - """ - R = self.codomain().base_ring() - # if there is a fraction field normalize the point so that -diff --git a/src/sage/schemes/product_projective/subscheme.py b/src/sage/schemes/product_projective/subscheme.py -index 32c9048..7d00e1e 100644 ---- a/src/sage/schemes/product_projective/subscheme.py -+++ b/src/sage/schemes/product_projective/subscheme.py -@@ -380,8 +380,8 @@ class AlgebraicScheme_subscheme_product_projective(AlgebraicScheme_subscheme_pro - sage: PP.<x,y,u,v> = ProductProjectiveSpaces(QQ, [1,1]) - sage: G = PP.subscheme([(x^2 + 1/4*y^2)*v - y^2*u]) - sage: D = PP.subscheme([x*v - y*u]) -- sage: G.intersection(D).rational_points() -- [(1 : 0 , 1 : 0), (1/2 : 1 , 1/2 : 1)] -+ sage: sorted(G.intersection(D).rational_points()) -+ [(1/2 : 1 , 1/2 : 1), (1 : 0 , 1 : 0)] - sage: Q = PP([1/2,1,1/2,1]) - sage: G.intersection_multiplicity(D, Q) - 2 -diff --git a/src/sage/schemes/projective/projective_homset.py b/src/sage/schemes/projective/projective_homset.py -index df8acaa..8ed8c8a 100644 ---- a/src/sage/schemes/projective/projective_homset.py -+++ b/src/sage/schemes/projective/projective_homset.py -@@ -143,14 +143,14 @@ class SchemeHomset_points_projective_field(SchemeHomset_points): - - sage: P.<x,y,z> = ProjectiveSpace(CC, 2) - sage: E = P.subscheme([y^3 - x^3 - x*z^2, x*y*z]) -- sage: L=E(P.base_ring()).points();L -+ sage: L=E(P.base_ring()).points(); sorted(L, key=str) - verbose 0 (71: projective_homset.py, points) Warning: computations in the numerical fields are inexact;points may be computed partially or incorrectly. - [(-0.500000000000000 + 0.866025403784439*I : 1.00000000000000 : 0.000000000000000), - (-0.500000000000000 - 0.866025403784439*I : 1.00000000000000 : 0.000000000000000), - (-1.00000000000000*I : 0.000000000000000 : 1.00000000000000), - (0.000000000000000 : 0.000000000000000 : 1.00000000000000), -- (1.00000000000000*I : 0.000000000000000 : 1.00000000000000), -- (1.00000000000000 : 1.00000000000000 : 0.000000000000000)] -+ (1.00000000000000 : 1.00000000000000 : 0.000000000000000), -+ (1.00000000000000*I : 0.000000000000000 : 1.00000000000000)] - sage: L[0].codomain() - Projective Space of dimension 2 over Complex Field with 53 bits of precision - -diff --git a/src/sage/schemes/projective/projective_point.py b/src/sage/schemes/projective/projective_point.py -index 351b490..e6793c4 100644 ---- a/src/sage/schemes/projective/projective_point.py -+++ b/src/sage/schemes/projective/projective_point.py -@@ -369,12 +369,8 @@ class SchemeMorphism_point_projective_ring(SchemeMorphism_point): - EXAMPLES:: - - sage: P.<x,y> = ProjectiveSpace(ZZ, 1) -- sage: hash(P([1, 1])) -- 1300952125 # 32-bit -- 3713081631935493181 # 64-bit -- sage: hash(P.point([2, 2], False)) -- 1300952125 # 32-bit -- 3713081631935493181 # 64-bit -+ sage: hash(P([1, 1])) == hash(P.point([2, 2], False)) -+ True - - :: - -@@ -382,12 +378,8 @@ class SchemeMorphism_point_projective_ring(SchemeMorphism_point): - sage: K.<w> = NumberField(x^2 + 3) - sage: O = K.maximal_order() - sage: P.<x,y> = ProjectiveSpace(O, 1) -- sage: hash(P([1+w, 2])) -- -1562365407 # 32-bit -- 1251212645657227809 # 64-bit -- sage: hash(P([2, 1-w])) -- -1562365407 # 32-bit -- 1251212645657227809 # 64-bit -+ sage: hash(P([1+w, 2])) == hash(P([2, 1-w])) -+ True - - TESTS:: - -@@ -1097,12 +1089,8 @@ class SchemeMorphism_point_projective_field(SchemeMorphism_point_projective_ring - EXAMPLES:: - - sage: P.<x,y> = ProjectiveSpace(QQ, 1) -- sage: hash(P([1/2, 1])) -- -1503642134 # 32-bit -- -6819944855328768534 # 64-bit -- sage: hash(P.point([1, 2], False)) -- -1503642134 # 32-bit -- -6819944855328768534 # 64-bit -+ sage: hash(P([1/2, 1])) == hash(P.point([1, 2], False)) -+ True - """ - P = copy(self) - P.normalize_coordinates() -diff --git a/src/sage/schemes/riemann_surfaces/riemann_surface.py b/src/sage/schemes/riemann_surfaces/riemann_surface.py -index ef5fcf5..cdc6486 100644 ---- a/src/sage/schemes/riemann_surfaces/riemann_surface.py -+++ b/src/sage/schemes/riemann_surfaces/riemann_surface.py -@@ -352,8 +352,8 @@ class RiemannSurface(object): - - sage: S = RiemannSurface(f, prec=100); S - Riemann surface defined by polynomial f = -z^3 + w^2 + 1 = 0, with 100 bits of precision -- sage: S.riemann_matrix() #abs tol 0.00000001 -- [0.500000000000000000000000... + 0.866025403784438646763723...*I] -+ sage: S.riemann_matrix()^6 #abs tol 0.00000001 -+ [1.0000000000000000000000000000 - 1.1832913578315177081175928479e-30*I] - - We can also work with Riemann surfaces that are defined over fields with a - complex embedding, but since the current interface for computing genus and -diff --git a/src/sage/schemes/toric/fano_variety.py b/src/sage/schemes/toric/fano_variety.py -index 78357a1..227c582 100644 ---- a/src/sage/schemes/toric/fano_variety.py -+++ b/src/sage/schemes/toric/fano_variety.py -@@ -449,7 +449,7 @@ def CPRFanoToricVariety(Delta=None, - N(-1, 0) - in 2-d lattice N - sage: [cone.ambient_ray_indices() for cone in FTV.fan()] -- [(0, 1), (1, 2), (3, 4), (2, 4), (0, 3)] -+ [(0, 1), (1, 2), (2, 4), (3, 4), (0, 3)] - - If charts are wrong, it should be detected:: - -diff --git a/src/sage/schemes/toric/morphism.py b/src/sage/schemes/toric/morphism.py -index d2cee6f..3de9544 100644 ---- a/src/sage/schemes/toric/morphism.py -+++ b/src/sage/schemes/toric/morphism.py -@@ -269,17 +269,17 @@ It is possible to study fibers of the last two morphisms or their composition:: - From: 3-d affine toric variety - To: 2-d toric variety covered by 3 affine patches - Defn: Defined on coordinates by sending [z0 : z1 : z2] to -- [z0^2*z1*z2^3 : z1*z2 : 1] -+ [1 : z1*z2 : z0^2*z1*z2^3] - sage: phi_d.codomain().fan().rays() -- N( 1, 0, 0), -+ N(-1, -1, 0), - N( 0, 1, 0), -- N(-1, -1, 0) -+ N( 1, 0, 0) - in Sublattice <N(1, 0, 0), N(0, 1, 0)> - sage: for c in phi_d.codomain().fan(): - ....: c.ambient_ray_indices() -- (1, 2) -- (0, 2) - (0, 1) -+ (0, 2) -+ (1, 2) - - We see that codomain fan of this morphism is a projective plane, which can be - verified by :: -@@ -321,13 +321,13 @@ corresponding to the cones of the domain fan:: - ....: c.ambient_ray_indices(), fc, fc.fan().nrays(), - ....: m, fm.image_cone(c).ambient_ray_indices())) - () |-> 1-d affine toric variety (0 rays, multiplicity 2) over () -- (0,) |-> 1-d affine toric variety (0 rays, multiplicity 1) over (0,) -- (1,) |-> 2-d affine toric variety (2 rays, multiplicity 1) over (0, 1) -- (2,) |-> 2-d affine toric variety (2 rays, multiplicity 1) over (0, 1) -- (0, 1) |-> 1-d affine toric variety (1 rays, multiplicity 1) over (0, 1) -- (1, 2) |-> 1-d affine toric variety (1 rays, multiplicity 1) over (0, 1) -- (0, 2) |-> 1-d affine toric variety (1 rays, multiplicity 1) over (0, 1) -- (0, 1, 2) |-> 0-d affine toric variety (0 rays, multiplicity 1) over (0, 1) -+ (0,) |-> 1-d affine toric variety (0 rays, multiplicity 1) over (2,) -+ (1,) |-> 2-d affine toric variety (2 rays, multiplicity 1) over (1, 2) -+ (2,) |-> 2-d affine toric variety (2 rays, multiplicity 1) over (1, 2) -+ (0, 1) |-> 1-d affine toric variety (1 rays, multiplicity 1) over (1, 2) -+ (1, 2) |-> 1-d affine toric variety (1 rays, multiplicity 1) over (1, 2) -+ (0, 2) |-> 1-d affine toric variety (1 rays, multiplicity 1) over (1, 2) -+ (0, 1, 2) |-> 0-d affine toric variety (0 rays, multiplicity 1) over (1, 2) - - Now we see that over one of the coordinate lines of the projective plane we also - have one-dimensional tori (but only one in each fiber), while over one of the -@@ -340,12 +340,12 @@ fan:: - ....: fm.index(c), c.ambient_ray_indices(), - ....: len(fm.primitive_preimage_cones(c)))) - 2 connected components over (), each with 1 irreducible components. -- 1 connected components over (0,), each with 1 irreducible components. -+ None connected components over (0,), each with 0 irreducible components. - None connected components over (1,), each with 0 irreducible components. -- None connected components over (2,), each with 0 irreducible components. -- None connected components over (1, 2), each with 0 irreducible components. -+ 1 connected components over (2,), each with 1 irreducible components. -+ None connected components over (0, 1), each with 0 irreducible components. - None connected components over (0, 2), each with 0 irreducible components. -- 1 connected components over (0, 1), each with 2 irreducible components. -+ 1 connected components over (1, 2), each with 2 irreducible components. - """ - - #***************************************************************************** -@@ -1046,7 +1046,7 @@ class SchemeMorphism_fan_toric_variety(SchemeMorphism, Morphism): - From: 2-d affine toric variety - To: 2-d toric variety covered by 3 affine patches - Defn: Defined on coordinates by sending [z0 : z1] to -- [z0*z1 : z1 : 1] -+ [1 : z1 : z0*z1] - - Coordinate plane inclusion (injective):: - -@@ -1055,7 +1055,7 @@ class SchemeMorphism_fan_toric_variety(SchemeMorphism, Morphism): - From: 2-d toric variety covered by 3 affine patches - To: 3-d CPR-Fano toric variety covered by 4 affine patches - Defn: Defined on coordinates by sending [z0 : z1 : z2] to -- [z0 : z1 : z2 : z2] -+ [z2 : z1 : z0 : z0] - """ - phi_i, phi_b, phi_s = self.fan_morphism().factor() - from sage.schemes.toric.all import ToricVariety -@@ -1693,7 +1693,7 @@ class SchemeMorphism_fan_fiber_component_toric_variety(SchemeMorphism): - From: 2-d toric variety covered by 4 affine patches - To: 4-d toric variety covered by 23 affine patches - Defn: Defined on coordinates by sending [z0 : z1 : z2 : z3] to -- [1 : 1 : 1 : 1 : z1 : 0 : 1 : z0 : 1 : 1 : 1 : z2 : z3 : 1 : 1] -+ [1 : 1 : 1 : 1 : z3 : 0 : 1 : z2 : 1 : 1 : 1 : z1 : z0 : 1 : 1] - sage: type(fiber_component.embedding_morphism()) - <class 'sage.schemes.toric.morphism.SchemeMorphism_fan_fiber_component_toric_variety'> - """ -@@ -1776,7 +1776,7 @@ class SchemeMorphism_fan_fiber_component_toric_variety(SchemeMorphism): - From: 2-d toric variety covered by 4 affine patches - To: 4-d toric variety covered by 23 affine patches - Defn: Defined on coordinates by sending [z0 : z1 : z2 : z3] to -- [1 : 1 : 1 : 1 : z1 : 0 : 1 : z0 : 1 : 1 : 1 : z2 : z3 : 1 : 1] -+ [1 : 1 : 1 : 1 : z3 : 0 : 1 : z2 : 1 : 1 : 1 : z1 : z0 : 1 : 1] - - sage: primitive_cone = Cone([(-1, 2, -1, 0)]) - sage: f = fibration.fiber_component(primitive_cone).embedding_morphism() -@@ -1950,9 +1950,9 @@ class SchemeMorphism_fan_fiber_component_toric_variety(SchemeMorphism): - sage: f = fc.embedding_morphism() - sage: for r in fc.fan().rays(): - ....: print("{} {}".format(r, f._image_ray_multiplicity(r))) -+ N(-1, 2) (11, 1) - N(0, 1) (5, 1) - N(1, -3) (9, 2) -- N(-1, 2) (11, 1) - sage: f._ray_index_map - {N(-3, 4): 10, N(-1, 2): 11, N(0, 1): 5, N(1, 0): 4, N(2, -6): 9} - """ -@@ -1998,10 +1998,10 @@ class SchemeMorphism_fan_fiber_component_toric_variety(SchemeMorphism): - V(z0) + V(z1) + 3*V(z2) + 4*V(z3) - sage: fc = f.fiber_component(Cone([(1,1,0)])) - sage: fc.embedding_morphism().pullback_divisor(D) -- 3*V(z0) + 2*V(z2) -+ 2*V(z0) + 3*V(z1) - sage: fc = f.fiber_component(Cone([(1,0,0)])) - sage: fc.embedding_morphism().pullback_divisor(D) -- -3*V(z0) - 3*V(z1) - V(z2) -+ -V(z0) - 3*V(z1) - 3*V(z2) - """ - from sage.schemes.toric.divisor import is_ToricDivisor - if not (is_ToricDivisor(divisor) and divisor.is_QQ_Cartier()): -diff --git a/src/sage/sets/set_from_iterator.py b/src/sage/sets/set_from_iterator.py -index b243290..3a352c1 100644 ---- a/src/sage/sets/set_from_iterator.py -+++ b/src/sage/sets/set_from_iterator.py -@@ -187,9 +187,8 @@ class EnumeratedSetFromIterator(Parent): - - sage: from sage.sets.set_from_iterator import EnumeratedSetFromIterator - sage: E = EnumeratedSetFromIterator(xsrange, (1,200)) -- sage: hash(E) -- 4600916458883504074 # 64-bit -- -2063607862 # 32-bit -+ sage: hash(E) == hash(tuple(range(1, 14))) -+ True - """ - try: - return hash(self._cache[:13]) -diff --git a/src/sage/structure/sequence.py b/src/sage/structure/sequence.py -index 238b655..375bbda 100644 ---- a/src/sage/structure/sequence.py -+++ b/src/sage/structure/sequence.py -@@ -173,9 +173,8 @@ def Sequence(x, universe=None, check=True, immutable=False, cr=False, cr_str=Non - that.:: - - sage: v = Sequence(range(10), ZZ, immutable=True) -- sage: hash(v) -- 1591723448 # 32-bit -- -4181190870548101704 # 64-bit -+ sage: hash(v) == hash(tuple(range(10))) -+ True - - - If you really know what you are doing, you can circumvent the type -@@ -360,9 +359,8 @@ class Sequence_generic(sage.structure.sage_object.SageObject, list): - :: - - sage: v = Sequence(range(10), ZZ, immutable=True) -- sage: hash(v) -- 1591723448 # 32-bit -- -4181190870548101704 # 64-bit -+ sage: hash(v) == hash(tuple(range(10))) -+ True - - - If you really know what you are doing, you can circumvent the type -@@ -640,12 +638,8 @@ class Sequence_generic(sage.structure.sage_object.SageObject, list): - ValueError: mutable sequences are unhashable - sage: a[0] = 10 - sage: a.set_immutable() -- sage: a.__hash__() -- -123014399 # 32-bit -- -5823618793256324351 # 64-bit -- sage: hash(a) -- -123014399 # 32-bit -- -5823618793256324351 # 64-bit -+ sage: a.__hash__() == hash(a) == hash(tuple(a)) -+ True - """ - if not self._is_immutable: - raise ValueError("mutable sequences are unhashable") -@@ -827,9 +821,9 @@ class Sequence_generic(sage.structure.sage_object.SageObject, list): - sage: t = copy(s) - sage: t == s - True -- sage: t.is_immutable == s.is_immutable -+ sage: t.is_immutable() == s.is_immutable() - True -- sage: t.is_mutable == s.is_mutable -+ sage: t.is_mutable() == s.is_mutable() - True - - """ -diff --git a/src/sage_setup/docbuild/utils.py b/src/sage_setup/docbuild/utils.py -index 9fce8e4..056392a 100644 ---- a/src/sage_setup/docbuild/utils.py -+++ b/src/sage_setup/docbuild/utils.py -@@ -112,16 +112,22 @@ def build_many(target, args, processes=None): - ... - WorkerDiedException: worker for 4 died with non-zero exit code -9 - """ -- from multiprocessing import Process, Queue, cpu_count -+ import multiprocessing -+ from multiprocessing import Process, Queue, cpu_count, set_start_method -+ # With OS X, Python 3.8 defaults to use 'spawn' instead of 'fork' -+ # in multiprocessing, and Sage docbuilding doesn't work with -+ # 'spawn'. See trac #27754. -+ if os.uname().sysname == 'Darwin': -+ set_start_method('fork', force=True) - from queue import Empty - - if processes is None: -- processes = cpu_count() -+ processes = multiprocessing.cpu_count() - - workers = [None] * processes - tasks = enumerate(args) - results = [] -- result_queue = Queue() -+ result_queue = multiprocessing.Queue() - - ### Utility functions ### - def run_worker(target, queue, idx, task): -@@ -222,7 +228,7 @@ def build_many(target, args, processes=None): - except StopIteration: - pass - else: -- w = Process(target=run_worker, -+ w = multiprocessing.Process(target=run_worker, - args=((target, result_queue) + task)) - w.start() - # Pair the new worker with the task it's performing (mostly -diff --git a/src/setup.py b/src/setup.py -index f7e04e6..01dd6c9 100755 ---- a/src/setup.py -+++ b/src/setup.py -@@ -8,6 +8,12 @@ import time - from distutils import log - from distutils.core import setup - -+# Work around a Cython problem in Python 3.8.x on macOS -+# https://github.com/cython/cython/issues/3262 -+if os.uname().sysname == 'Darwin': -+ import multiprocessing -+ multiprocessing.set_start_method('fork', force=True) -+ - ######################################################### - ### Set source directory - ######################################################### |