From 63df8b790d52b2d45cdd8060099931486914ce34 Mon Sep 17 00:00:00 2001 From: zabrocki Date: Thu, 11 Jun 2015 07:21:35 -0500 Subject: [PATCH 1/8] removed most instances of choose_nk and split_nk, choose_nk.from_rank and choose_nk.rank seem to remain --- src/doc/en/reference/combinat/module_list.rst | 2 - src/sage/combinat/choose_nk.py | 189 ------------------ src/sage/combinat/combination.py | 25 --- src/sage/combinat/enumerated_sets.py | 2 - src/sage/combinat/set_partition_ordered.py | 27 --- src/sage/combinat/split_nk.py | 61 ------ src/sage/combinat/subset.py | 1 - 7 files changed, 307 deletions(-) delete mode 100644 src/sage/combinat/choose_nk.py delete mode 100644 src/sage/combinat/split_nk.py diff --git a/src/doc/en/reference/combinat/module_list.rst b/src/doc/en/reference/combinat/module_list.rst index b5a90e17e12..ba02d240deb 100644 --- a/src/doc/en/reference/combinat/module_list.rst +++ b/src/doc/en/reference/combinat/module_list.rst @@ -27,7 +27,6 @@ Comprehensive Module list sage/combinat/binary_tree sage/combinat/cartesian_product sage/combinat/catalog_partitions - sage/combinat/choose_nk sage/combinat/cluster_algebra_quiver/__init__ sage/combinat/cluster_algebra_quiver/all sage/combinat/cluster_algebra_quiver/cluster_seed @@ -299,7 +298,6 @@ Comprehensive Module list sage/combinat/species/structure sage/combinat/species/subset_species sage/combinat/species/sum_species - sage/combinat/split_nk sage/combinat/subset sage/combinat/subsets_hereditary sage/combinat/subsets_pairwise diff --git a/src/sage/combinat/choose_nk.py b/src/sage/combinat/choose_nk.py deleted file mode 100644 index faa48df8beb..00000000000 --- a/src/sage/combinat/choose_nk.py +++ /dev/null @@ -1,189 +0,0 @@ -""" -Deprecated combinations - -AUTHORS: - -- Mike Hansen (2007): initial implementation - -- Vincent Delecroix (2014): deprecation -""" -#***************************************************************************** -# Copyright (C) 2007 Mike Hansen , -# -# Distributed under the terms of the GNU General Public License (GPL) -# -# This code is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -# General Public License for more details. -# -# The full text of the GPL is available at: -# -# http://www.gnu.org/licenses/ -#***************************************************************************** -from sage.rings.arith import binomial - -def ChooseNK(n, k): - """ - All possible choices of k elements out of range(n) without repetitions. - - The elements of the output are tuples of Python int (and not Sage Integer). - - This was deprecated in :trac:`10534` for :func:`Combinations` - (or ``itertools.combinations`` for doing iteration). - - EXAMPLES:: - - sage: from sage.combinat.choose_nk import ChooseNK - sage: c = ChooseNK(4,2) - doctest:...: DeprecationWarning: ChooseNk is deprecated and will be - removed. Use Combinations instead (or combinations from the itertools - module for iteration) - See http://trac.sagemath.org/10534 for details. - sage: c.first() - [0, 1] - sage: c.list() - [[0, 1], [0, 2], [0, 3], [1, 2], [1, 3], [2, 3]] - """ - from sage.misc.superseded import deprecation - deprecation(10534, "ChooseNk is deprecated and will be removed. Use Combinations instead (or combinations from the itertools module for iteration)") - from sage.combinat.combination import Combinations - return Combinations(n,k) - -#TODO: the following functions are used sage.combinat.combination and -# sage.combinat.subset. It might be good to move them somewhere else. -def rank(comb, n, check=True): - """ - Return the rank of ``comb`` in the subsets of ``range(n)`` of size ``k`` - where ``k`` is the length of ``comb``. - - The algorithm used is based on combinadics and James McCaffrey's - MSDN article. See: :wikipedia:`Combinadic`. - - EXAMPLES:: - - sage: import sage.combinat.choose_nk as choose_nk - sage: choose_nk.rank((), 3) - 0 - sage: choose_nk.rank((0,), 3) - 0 - sage: choose_nk.rank((1,), 3) - 1 - sage: choose_nk.rank((2,), 3) - 2 - sage: choose_nk.rank((0,1), 3) - 0 - sage: choose_nk.rank((0,2), 3) - 1 - sage: choose_nk.rank((1,2), 3) - 2 - sage: choose_nk.rank((0,1,2), 3) - 0 - - sage: choose_nk.rank((0,1,2,3), 3) - Traceback (most recent call last): - ... - ValueError: len(comb) must be <= n - sage: choose_nk.rank((0,0), 2) - Traceback (most recent call last): - ... - ValueError: comb must be a subword of (0,1,...,n) - - sage: choose_nk.rank([1,2], 3) - 2 - sage: choose_nk.rank([0,1,2], 3) - 0 - """ - k = len(comb) - if check: - if k > n: - raise ValueError("len(comb) must be <= n") - comb = [int(_) for _ in comb] - for i in xrange(k - 1): - if comb[i + 1] <= comb[i]: - raise ValueError("comb must be a subword of (0,1,...,n)") - - #Generate the combinadic from the - #combination - - #w = [n-1-comb[i] for i in xrange(k)] - - #Calculate the integer that is the dual of - #the lexicographic index of the combination - r = k - t = 0 - for i in range(k): - t += binomial(n - 1 - comb[i], r) - r -= 1 - - return binomial(n,k)-t-1 - - - -def _comb_largest(a,b,x): - """ - Returns the largest w < a such that binomial(w,b) <= x. - - EXAMPLES:: - - sage: from sage.combinat.choose_nk import _comb_largest - sage: _comb_largest(6,3,10) - 5 - sage: _comb_largest(6,3,5) - 4 - """ - w = a - 1 - - while binomial(w,b) > x: - w -= 1 - - return w - -def from_rank(r, n, k): - """ - Returns the combination of rank r in the subsets of range(n) of - size k when listed in lexicographic order. - - The algorithm used is based on combinadics and James McCaffrey's - MSDN article. See: http://en.wikipedia.org/wiki/Combinadic - - EXAMPLES:: - - sage: import sage.combinat.choose_nk as choose_nk - sage: choose_nk.from_rank(0,3,0) - () - sage: choose_nk.from_rank(0,3,1) - (0,) - sage: choose_nk.from_rank(1,3,1) - (1,) - sage: choose_nk.from_rank(2,3,1) - (2,) - sage: choose_nk.from_rank(0,3,2) - (0, 1) - sage: choose_nk.from_rank(1,3,2) - (0, 2) - sage: choose_nk.from_rank(2,3,2) - (1, 2) - sage: choose_nk.from_rank(0,3,3) - (0, 1, 2) - """ - if k < 0: - raise ValueError("k must be > 0") - if k > n: - raise ValueError("k must be <= n") - - a = n - b = k - x = binomial(n, k) - 1 - r # x is the 'dual' of m - comb = [None] * k - - for i in xrange(k): - comb[i] = _comb_largest(a, b, x) - x = x - binomial(comb[i], b) - a = comb[i] - b = b - 1 - - for i in xrange(k): - comb[i] = (n - 1) - comb[i] - - return tuple(comb) diff --git a/src/sage/combinat/combination.py b/src/sage/combinat/combination.py index e72bce63ae7..00dadb2a0fe 100644 --- a/src/sage/combinat/combination.py +++ b/src/sage/combinat/combination.py @@ -27,7 +27,6 @@ from sage.rings.all import ZZ, Integer from sage.rings.arith import binomial from combinat import CombinatorialClass -from choose_nk import rank, from_rank from integer_vector import IntegerVectors from sage.misc.misc import uniq @@ -465,27 +464,3 @@ def rank(self, x): x = [self.mset.index(_) for _ in x] return rank(x, len(self.mset)) - -########################################################## -# Deprecations - -class ChooseNK(Combinations_setk): - def __setstate__(self, state): - r""" - For unpickling old ``ChooseNK`` objects. - - TESTS:: - - sage: loads("x\x9ck`J.NLO\xd5K\xce\xcfM\xca\xccK,\xd1K\xce\xc8\xcf" - ....: "/N\x8d\xcf\xcb\xe6r\x06\xb3\xfc\xbc\xb9\n\x195\x1b\x0b" - ....: "\x99j\x0b\x995B\x99\xe2\xf3\nY :\x8a2\xf3\xd2\x8b\xf52" - ....: "\xf3JR\xd3S\x8b\xb8r\x13\xb3S\xe3a\x9cB\xd6PF\xd3\xd6\xa0" - ....: "B6\xa0\xfa\xecB\xf6\x0c \xd7\x08\xc8\xe5(M\xd2\x03\x00{" - ....: "\x82$\xd8") - Combinations of [0, 1, 2, 3, 4] of length 2 - """ - self.__class__ = Combinations_setk - Combinations_setk.__init__(self, range(state['_n']), state['_k']) - -from sage.structure.sage_object import register_unpickle_override -register_unpickle_override("sage.combinat.choose_nk", "ChooseNK", ChooseNK) diff --git a/src/sage/combinat/enumerated_sets.py b/src/sage/combinat/enumerated_sets.py index a39220a900e..ce295b1dff8 100644 --- a/src/sage/combinat/enumerated_sets.py +++ b/src/sage/combinat/enumerated_sets.py @@ -130,8 +130,6 @@ ------------------------- - :ref:`sage.combinat.permutation_nk` -- :ref:`sage.combinat.split_nk` -- :ref:`sage.combinat.choose_nk` - :ref:`sage.combinat.multichoose_nk` - :ref:`sage.combinat.gray_codes` diff --git a/src/sage/combinat/set_partition_ordered.py b/src/sage/combinat/set_partition_ordered.py index 908401920fd..e42b52b3b37 100644 --- a/src/sage/combinat/set_partition_ordered.py +++ b/src/sage/combinat/set_partition_ordered.py @@ -585,30 +585,3 @@ def __iter__(self): yield self.element_class(self, [Set(res[dcomp[i]+1:dcomp[i+1]+1]) for i in range(l)]) -########################################################## -# Deprecations - - -class SplitNK(OrderedSetPartitions_scomp): - def __setstate__(self, state): - r""" - For unpickling old ``SplitNK`` objects. - - TESTS:: - - sage: loads("x\x9ck`J.NLO\xd5K\xce\xcfM\xca\xccK,\xd1+.\xc8\xc9," - ....: "\x89\xcf\xcb\xe6\n\x061\xfc\xbcA\xccBF\xcd\xc6B\xa6\xda" - ....: "Bf\x8dP\xa6\xf8\xbcB\x16\x88\x96\xa2\xcc\xbc\xf4b\xbd\xcc" - ....: "\xbc\x92\xd4\xf4\xd4\"\xae\xdc\xc4\xec\xd4x\x18\xa7\x905" - ....: "\x94\xd1\xb45\xa8\x90\r\xa8>\xbb\x90=\x03\xc85\x02r9J\x93" - ....: "\xf4\x00\xb4\xc6%f") - Ordered set partitions of {0, 1, 2, 3, 4} into parts of size [2, 3] - """ - self.__class__ = OrderedSetPartitions_scomp - n = state['_n'] - k = state['_k'] - OrderedSetPartitions_scomp.__init__(self, range(state['_n']), (k,n-k)) - -from sage.structure.sage_object import register_unpickle_override -register_unpickle_override("sage.combinat.split_nk", "SplitNK_nk", SplitNK) - diff --git a/src/sage/combinat/split_nk.py b/src/sage/combinat/split_nk.py deleted file mode 100644 index 93ae9f754f7..00000000000 --- a/src/sage/combinat/split_nk.py +++ /dev/null @@ -1,61 +0,0 @@ -""" -Derecated splits - -Authors: - -- Mike Hansen (2007): original version - -- Vincent Delecroix (2014): deprecation -""" -#***************************************************************************** -# Copyright (C) 2007 Mike Hansen , -# -# Distributed under the terms of the GNU General Public License (GPL) -# -# This code is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -# General Public License for more details. -# -# The full text of the GPL is available at: -# -# http://www.gnu.org/licenses/ -#***************************************************************************** - -def SplitNK(n, k): - """ - Returns the combinatorial class of splits of a the set range(n) - into a set of size k and a set of size n-k. - - This was deprecated in :trac:`10534`. Use instead - :class:`OrderedSetPartitions`. - - EXAMPLES:: - - sage: from sage.combinat.split_nk import SplitNK - sage: S = SplitNK(5,2) - doctest:...: DeprecationWarning: SplitNk is deprecated and will be - removed. Use OrderedSetPartitions instead. - See http://trac.sagemath.org/10534 for details. - sage: S - Ordered set partitions of {0, 1, 2, 3, 4} into parts of size [2, 3] - sage: S.first() - [{0, 1}, {2, 3, 4}] - sage: S.last() - [{3, 4}, {0, 1, 2}] - sage: S.list() - [[{0, 1}, {2, 3, 4}], - [{0, 2}, {1, 3, 4}], - [{0, 3}, {1, 2, 4}], - [{0, 4}, {1, 2, 3}], - [{1, 2}, {0, 3, 4}], - [{1, 3}, {0, 2, 4}], - [{1, 4}, {0, 2, 3}], - [{2, 3}, {0, 1, 4}], - [{2, 4}, {0, 1, 3}], - [{3, 4}, {0, 1, 2}]] - """ - from sage.misc.superseded import deprecation - from sage.combinat.set_partition_ordered import OrderedSetPartitions - deprecation(10534, "SplitNk is deprecated and will be removed. Use OrderedSetPartitions instead.") - return OrderedSetPartitions(range(n), [k, n-k]) diff --git a/src/sage/combinat/subset.py b/src/sage/combinat/subset.py index 39aff81e561..082fde42379 100644 --- a/src/sage/combinat/subset.py +++ b/src/sage/combinat/subset.py @@ -41,7 +41,6 @@ from sage.rings.arith import binomial from sage.rings.integer_ring import ZZ from sage.rings.integer import Integer -import choose_nk ZZ_0 = ZZ.zero() From 5258e5ed24489ece0d699f32a841df7fc1808921 Mon Sep 17 00:00:00 2001 From: zabrocki Date: Thu, 11 Jun 2015 07:48:59 -0500 Subject: [PATCH 2/8] saved the functions rank and from_rank in choose_nk.py --- src/sage/combinat/combination.py | 1 + src/sage/combinat/subset.py | 1 + 2 files changed, 2 insertions(+) diff --git a/src/sage/combinat/combination.py b/src/sage/combinat/combination.py index 00dadb2a0fe..ba11496a418 100644 --- a/src/sage/combinat/combination.py +++ b/src/sage/combinat/combination.py @@ -29,6 +29,7 @@ from combinat import CombinatorialClass from integer_vector import IntegerVectors from sage.misc.misc import uniq +from choose_nk import rank, from_rank def Combinations(mset, k=None): """ diff --git a/src/sage/combinat/subset.py b/src/sage/combinat/subset.py index 082fde42379..39aff81e561 100644 --- a/src/sage/combinat/subset.py +++ b/src/sage/combinat/subset.py @@ -41,6 +41,7 @@ from sage.rings.arith import binomial from sage.rings.integer_ring import ZZ from sage.rings.integer import Integer +import choose_nk ZZ_0 = ZZ.zero() From ec6c8c9bf60fafdc0e20887b1620b5271daf9ec4 Mon Sep 17 00:00:00 2001 From: zabrocki Date: Thu, 11 Jun 2015 07:50:51 -0500 Subject: [PATCH 3/8] readded file choose_nk.py --- src/sage/combinat/choose_nk.py | 162 +++++++++++++++++++++++++++++++++ 1 file changed, 162 insertions(+) create mode 100644 src/sage/combinat/choose_nk.py diff --git a/src/sage/combinat/choose_nk.py b/src/sage/combinat/choose_nk.py new file mode 100644 index 00000000000..7e5da370c1d --- /dev/null +++ b/src/sage/combinat/choose_nk.py @@ -0,0 +1,162 @@ +""" +Deprecated combinations + +AUTHORS: + +- Mike Hansen (2007): initial implementation + +- Vincent Delecroix (2014): deprecation +""" +#***************************************************************************** +# Copyright (C) 2007 Mike Hansen , +# +# Distributed under the terms of the GNU General Public License (GPL) +# +# This code is distributed in the hope that it will be useful, +# but WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU +# General Public License for more details. +# +# The full text of the GPL is available at: +# +# http://www.gnu.org/licenses/ +#***************************************************************************** +from sage.rings.arith import binomial + +#TODO: the following functions are used sage.combinat.combination and +# sage.combinat.subset. It might be good to move them somewhere else. +def rank(comb, n, check=True): + """ + Return the rank of ``comb`` in the subsets of ``range(n)`` of size ``k`` + where ``k`` is the length of ``comb``. + + The algorithm used is based on combinadics and James McCaffrey's + MSDN article. See: :wikipedia:`Combinadic`. + + EXAMPLES:: + + sage: import sage.combinat.choose_nk as choose_nk + sage: choose_nk.rank((), 3) + 0 + sage: choose_nk.rank((0,), 3) + 0 + sage: choose_nk.rank((1,), 3) + 1 + sage: choose_nk.rank((2,), 3) + 2 + sage: choose_nk.rank((0,1), 3) + 0 + sage: choose_nk.rank((0,2), 3) + 1 + sage: choose_nk.rank((1,2), 3) + 2 + sage: choose_nk.rank((0,1,2), 3) + 0 + + sage: choose_nk.rank((0,1,2,3), 3) + Traceback (most recent call last): + ... + ValueError: len(comb) must be <= n + sage: choose_nk.rank((0,0), 2) + Traceback (most recent call last): + ... + ValueError: comb must be a subword of (0,1,...,n) + + sage: choose_nk.rank([1,2], 3) + 2 + sage: choose_nk.rank([0,1,2], 3) + 0 + """ + k = len(comb) + if check: + if k > n: + raise ValueError("len(comb) must be <= n") + comb = [int(_) for _ in comb] + for i in xrange(k - 1): + if comb[i + 1] <= comb[i]: + raise ValueError("comb must be a subword of (0,1,...,n)") + + #Generate the combinadic from the + #combination + + #w = [n-1-comb[i] for i in xrange(k)] + + #Calculate the integer that is the dual of + #the lexicographic index of the combination + r = k + t = 0 + for i in range(k): + t += binomial(n - 1 - comb[i], r) + r -= 1 + + return binomial(n,k)-t-1 + + + +def _comb_largest(a,b,x): + """ + Returns the largest w < a such that binomial(w,b) <= x. + + EXAMPLES:: + + sage: from sage.combinat.choose_nk import _comb_largest + sage: _comb_largest(6,3,10) + 5 + sage: _comb_largest(6,3,5) + 4 + """ + w = a - 1 + + while binomial(w,b) > x: + w -= 1 + + return w + +def from_rank(r, n, k): + """ + Returns the combination of rank r in the subsets of range(n) of + size k when listed in lexicographic order. + + The algorithm used is based on combinadics and James McCaffrey's + MSDN article. See: http://en.wikipedia.org/wiki/Combinadic + + EXAMPLES:: + + sage: import sage.combinat.choose_nk as choose_nk + sage: choose_nk.from_rank(0,3,0) + () + sage: choose_nk.from_rank(0,3,1) + (0,) + sage: choose_nk.from_rank(1,3,1) + (1,) + sage: choose_nk.from_rank(2,3,1) + (2,) + sage: choose_nk.from_rank(0,3,2) + (0, 1) + sage: choose_nk.from_rank(1,3,2) + (0, 2) + sage: choose_nk.from_rank(2,3,2) + (1, 2) + sage: choose_nk.from_rank(0,3,3) + (0, 1, 2) + """ + if k < 0: + raise ValueError("k must be > 0") + if k > n: + raise ValueError("k must be <= n") + + a = n + b = k + x = binomial(n, k) - 1 - r # x is the 'dual' of m + comb = [None] * k + + for i in xrange(k): + comb[i] = _comb_largest(a, b, x) + x = x - binomial(comb[i], b) + a = comb[i] + b = b - 1 + + for i in xrange(k): + comb[i] = (n - 1) - comb[i] + + return tuple(comb) From 462efd556a38f382de865d9152a0dfb59185a5eb Mon Sep 17 00:00:00 2001 From: zabrocki Date: Thu, 11 Jun 2015 07:55:37 -0500 Subject: [PATCH 4/8] restore important lines --- src/sage/combinat/combination.py | 2 +- src/sage/combinat/enumerated_sets.py | 1 + 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/src/sage/combinat/combination.py b/src/sage/combinat/combination.py index ba11496a418..6cdc988b569 100644 --- a/src/sage/combinat/combination.py +++ b/src/sage/combinat/combination.py @@ -27,9 +27,9 @@ from sage.rings.all import ZZ, Integer from sage.rings.arith import binomial from combinat import CombinatorialClass +from choose_nk import rank, from_rank from integer_vector import IntegerVectors from sage.misc.misc import uniq -from choose_nk import rank, from_rank def Combinations(mset, k=None): """ diff --git a/src/sage/combinat/enumerated_sets.py b/src/sage/combinat/enumerated_sets.py index ce295b1dff8..3f789bd584c 100644 --- a/src/sage/combinat/enumerated_sets.py +++ b/src/sage/combinat/enumerated_sets.py @@ -130,6 +130,7 @@ ------------------------- - :ref:`sage.combinat.permutation_nk` +- :ref:`sage.combinat.choose_nk` - :ref:`sage.combinat.multichoose_nk` - :ref:`sage.combinat.gray_codes` From 7b35f5508523a517e1f213e9a6b53749e9b5e8ed Mon Sep 17 00:00:00 2001 From: zabrocki Date: Thu, 11 Jun 2015 15:03:00 -0500 Subject: [PATCH 5/8] restore pickles --- src/sage/combinat/combination.py | 24 +++++++++++++++++++ src/sage/combinat/set_partition_ordered.py | 27 ++++++++++++++++++++++ 2 files changed, 51 insertions(+) diff --git a/src/sage/combinat/combination.py b/src/sage/combinat/combination.py index 6cdc988b569..e72bce63ae7 100644 --- a/src/sage/combinat/combination.py +++ b/src/sage/combinat/combination.py @@ -465,3 +465,27 @@ def rank(self, x): x = [self.mset.index(_) for _ in x] return rank(x, len(self.mset)) + +########################################################## +# Deprecations + +class ChooseNK(Combinations_setk): + def __setstate__(self, state): + r""" + For unpickling old ``ChooseNK`` objects. + + TESTS:: + + sage: loads("x\x9ck`J.NLO\xd5K\xce\xcfM\xca\xccK,\xd1K\xce\xc8\xcf" + ....: "/N\x8d\xcf\xcb\xe6r\x06\xb3\xfc\xbc\xb9\n\x195\x1b\x0b" + ....: "\x99j\x0b\x995B\x99\xe2\xf3\nY :\x8a2\xf3\xd2\x8b\xf52" + ....: "\xf3JR\xd3S\x8b\xb8r\x13\xb3S\xe3a\x9cB\xd6PF\xd3\xd6\xa0" + ....: "B6\xa0\xfa\xecB\xf6\x0c \xd7\x08\xc8\xe5(M\xd2\x03\x00{" + ....: "\x82$\xd8") + Combinations of [0, 1, 2, 3, 4] of length 2 + """ + self.__class__ = Combinations_setk + Combinations_setk.__init__(self, range(state['_n']), state['_k']) + +from sage.structure.sage_object import register_unpickle_override +register_unpickle_override("sage.combinat.choose_nk", "ChooseNK", ChooseNK) diff --git a/src/sage/combinat/set_partition_ordered.py b/src/sage/combinat/set_partition_ordered.py index e42b52b3b37..908401920fd 100644 --- a/src/sage/combinat/set_partition_ordered.py +++ b/src/sage/combinat/set_partition_ordered.py @@ -585,3 +585,30 @@ def __iter__(self): yield self.element_class(self, [Set(res[dcomp[i]+1:dcomp[i+1]+1]) for i in range(l)]) +########################################################## +# Deprecations + + +class SplitNK(OrderedSetPartitions_scomp): + def __setstate__(self, state): + r""" + For unpickling old ``SplitNK`` objects. + + TESTS:: + + sage: loads("x\x9ck`J.NLO\xd5K\xce\xcfM\xca\xccK,\xd1+.\xc8\xc9," + ....: "\x89\xcf\xcb\xe6\n\x061\xfc\xbcA\xccBF\xcd\xc6B\xa6\xda" + ....: "Bf\x8dP\xa6\xf8\xbcB\x16\x88\x96\xa2\xcc\xbc\xf4b\xbd\xcc" + ....: "\xbc\x92\xd4\xf4\xd4\"\xae\xdc\xc4\xec\xd4x\x18\xa7\x905" + ....: "\x94\xd1\xb45\xa8\x90\r\xa8>\xbb\x90=\x03\xc85\x02r9J\x93" + ....: "\xf4\x00\xb4\xc6%f") + Ordered set partitions of {0, 1, 2, 3, 4} into parts of size [2, 3] + """ + self.__class__ = OrderedSetPartitions_scomp + n = state['_n'] + k = state['_k'] + OrderedSetPartitions_scomp.__init__(self, range(state['_n']), (k,n-k)) + +from sage.structure.sage_object import register_unpickle_override +register_unpickle_override("sage.combinat.split_nk", "SplitNK_nk", SplitNK) + From 97d0c13d737251f3b0e9b200ed20bb47bfc54e25 Mon Sep 17 00:00:00 2001 From: zabrocki Date: Mon, 2 Nov 2015 22:44:25 -0500 Subject: [PATCH 6/8] remove a few references to choose_nk, move functions in choose_nk.py to combination.py --- src/sage/combinat/choose_nk.py | 107 +++------------------ src/sage/combinat/combination.py | 135 ++++++++++++++++++++++++++- src/sage/combinat/enumerated_sets.py | 1 - src/sage/combinat/subset.py | 12 +-- 4 files changed, 155 insertions(+), 100 deletions(-) diff --git a/src/sage/combinat/choose_nk.py b/src/sage/combinat/choose_nk.py index 7e5da370c1d..2b0420f483e 100644 --- a/src/sage/combinat/choose_nk.py +++ b/src/sage/combinat/choose_nk.py @@ -1,30 +1,6 @@ -""" -Deprecated combinations +# the following functions have been moved to sage.combinat.combination +import sage.combinat.combination as combination -AUTHORS: - -- Mike Hansen (2007): initial implementation - -- Vincent Delecroix (2014): deprecation -""" -#***************************************************************************** -# Copyright (C) 2007 Mike Hansen , -# -# Distributed under the terms of the GNU General Public License (GPL) -# -# This code is distributed in the hope that it will be useful, -# but WITHOUT ANY WARRANTY; without even the implied warranty of -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU -# General Public License for more details. -# -# The full text of the GPL is available at: -# -# http://www.gnu.org/licenses/ -#***************************************************************************** -from sage.rings.arith import binomial - -#TODO: the following functions are used sage.combinat.combination and -# sage.combinat.subset. It might be good to move them somewhere else. def rank(comb, n, check=True): """ Return the rank of ``comb`` in the subsets of ``range(n)`` of size ``k`` @@ -37,6 +13,8 @@ def rank(comb, n, check=True): sage: import sage.combinat.choose_nk as choose_nk sage: choose_nk.rank((), 3) + doctest:1: DeprecationWarning: choose_nk.rank is deprecated and will be removed. Use combination.rank instead + See http://trac.sagemath.org/18674 for details. 0 sage: choose_nk.rank((0,), 3) 0 @@ -67,55 +45,14 @@ def rank(comb, n, check=True): sage: choose_nk.rank([0,1,2], 3) 0 """ - k = len(comb) - if check: - if k > n: - raise ValueError("len(comb) must be <= n") - comb = [int(_) for _ in comb] - for i in xrange(k - 1): - if comb[i + 1] <= comb[i]: - raise ValueError("comb must be a subword of (0,1,...,n)") - - #Generate the combinadic from the - #combination - - #w = [n-1-comb[i] for i in xrange(k)] - - #Calculate the integer that is the dual of - #the lexicographic index of the combination - r = k - t = 0 - for i in range(k): - t += binomial(n - 1 - comb[i], r) - r -= 1 - - return binomial(n,k)-t-1 - - - -def _comb_largest(a,b,x): - """ - Returns the largest w < a such that binomial(w,b) <= x. - - EXAMPLES:: - - sage: from sage.combinat.choose_nk import _comb_largest - sage: _comb_largest(6,3,10) - 5 - sage: _comb_largest(6,3,5) - 4 - """ - w = a - 1 - - while binomial(w,b) > x: - w -= 1 - - return w + from sage.misc.superseded import deprecation + deprecation(18674, "choose_nk.rank is deprecated and will be removed. Use combination.rank instead") + return combination.rank(comb, n, check) def from_rank(r, n, k): - """ - Returns the combination of rank r in the subsets of range(n) of - size k when listed in lexicographic order. + r""" + Returns the combination of rank ``r`` in the subsets of ``range(n)`` of + size ``k`` when listed in lexicographic order. The algorithm used is based on combinadics and James McCaffrey's MSDN article. See: http://en.wikipedia.org/wiki/Combinadic @@ -124,6 +61,8 @@ def from_rank(r, n, k): sage: import sage.combinat.choose_nk as choose_nk sage: choose_nk.from_rank(0,3,0) + doctest:1: DeprecationWarning: choose_nk.from_rank is deprecated and will be removed. Use combination.from_rank instead + See http://trac.sagemath.org/18674 for details. () sage: choose_nk.from_rank(0,3,1) (0,) @@ -140,23 +79,7 @@ def from_rank(r, n, k): sage: choose_nk.from_rank(0,3,3) (0, 1, 2) """ - if k < 0: - raise ValueError("k must be > 0") - if k > n: - raise ValueError("k must be <= n") - - a = n - b = k - x = binomial(n, k) - 1 - r # x is the 'dual' of m - comb = [None] * k - - for i in xrange(k): - comb[i] = _comb_largest(a, b, x) - x = x - binomial(comb[i], b) - a = comb[i] - b = b - 1 - - for i in xrange(k): - comb[i] = (n - 1) - comb[i] + from sage.misc.superseded import deprecation + deprecation(18674, "choose_nk.from_rank is deprecated and will be removed. Use combination.from_rank instead") + return combination.from_rank(r, n, k) - return tuple(comb) diff --git a/src/sage/combinat/combination.py b/src/sage/combinat/combination.py index e72bce63ae7..9b1680f2302 100644 --- a/src/sage/combinat/combination.py +++ b/src/sage/combinat/combination.py @@ -27,7 +27,6 @@ from sage.rings.all import ZZ, Integer from sage.rings.arith import binomial from combinat import CombinatorialClass -from choose_nk import rank, from_rank from integer_vector import IntegerVectors from sage.misc.misc import uniq @@ -466,6 +465,140 @@ def rank(self, x): return rank(x, len(self.mset)) +def rank(comb, n, check=True): + """ + Return the rank of ``comb`` in the subsets of ``range(n)`` of size ``k`` + where ``k`` is the length of ``comb``. + + The algorithm used is based on combinadics and James McCaffrey's + MSDN article. See: :wikipedia:`Combinadic`. + + EXAMPLES:: + + sage: import sage.combinat.combination as combination + sage: combination.rank((), 3) + 0 + sage: combination.rank((0,), 3) + 0 + sage: combination.rank((1,), 3) + 1 + sage: combination.rank((2,), 3) + 2 + sage: combination.rank((0,1), 3) + 0 + sage: combination.rank((0,2), 3) + 1 + sage: combination.rank((1,2), 3) + 2 + sage: combination.rank((0,1,2), 3) + 0 + + sage: combination.rank((0,1,2,3), 3) + Traceback (most recent call last): + ... + ValueError: len(comb) must be <= n + sage: combination.rank((0,0), 2) + Traceback (most recent call last): + ... + ValueError: comb must be a subword of (0,1,...,n) + + sage: combination.rank([1,2], 3) + 2 + sage: combination.rank([0,1,2], 3) + 0 + """ + k = len(comb) + if check: + if k > n: + raise ValueError("len(comb) must be <= n") + comb = [int(_) for _ in comb] + for i in xrange(k - 1): + if comb[i + 1] <= comb[i]: + raise ValueError("comb must be a subword of (0,1,...,n)") + + #Generate the combinadic from the + #combination + + #w = [n-1-comb[i] for i in xrange(k)] + + #Calculate the integer that is the dual of + #the lexicographic index of the combination + r = k + t = 0 + for i in range(k): + t += binomial(n - 1 - comb[i], r) + r -= 1 + + return binomial(n,k)-t-1 + +def _comb_largest(a,b,x): + r""" + Returns the largest `w < a` such that `binomial(w,b) <= x`. + + EXAMPLES:: + + sage: from sage.combinat.combination import _comb_largest + sage: _comb_largest(6,3,10) + 5 + sage: _comb_largest(6,3,5) + 4 + """ + w = a - 1 + + while binomial(w,b) > x: + w -= 1 + + return w + +def from_rank(r, n, k): + r""" + Returns the combination of rank ``r`` in the subsets of + ``range(n)`` of size ``k`` when listed in lexicographic order. + + The algorithm used is based on combinadics and James McCaffrey's + MSDN article. See: :wikipedia:`Combinadic` + + EXAMPLES:: + + sage: import sage.combinat.combination as combination + sage: combination.from_rank(0,3,0) + () + sage: combination.from_rank(0,3,1) + (0,) + sage: combination.from_rank(1,3,1) + (1,) + sage: combination.from_rank(2,3,1) + (2,) + sage: combination.from_rank(0,3,2) + (0, 1) + sage: combination.from_rank(1,3,2) + (0, 2) + sage: combination.from_rank(2,3,2) + (1, 2) + sage: combination.from_rank(0,3,3) + (0, 1, 2) + """ + if k < 0: + raise ValueError("k must be > 0") + if k > n: + raise ValueError("k must be <= n") + + a = n + b = k + x = binomial(n, k) - 1 - r # x is the 'dual' of m + comb = [None] * k + + for i in xrange(k): + comb[i] = _comb_largest(a, b, x) + x = x - binomial(comb[i], b) + a = comb[i] + b = b - 1 + + for i in xrange(k): + comb[i] = (n - 1) - comb[i] + + return tuple(comb) + ########################################################## # Deprecations diff --git a/src/sage/combinat/enumerated_sets.py b/src/sage/combinat/enumerated_sets.py index 291e861e286..7aeb4054a15 100644 --- a/src/sage/combinat/enumerated_sets.py +++ b/src/sage/combinat/enumerated_sets.py @@ -130,7 +130,6 @@ ------------------------- - :ref:`sage.combinat.permutation_nk` -- :ref:`sage.combinat.choose_nk` - :ref:`sage.combinat.multichoose_nk` - :ref:`sage.combinat.gray_codes` diff --git a/src/sage/combinat/subset.py b/src/sage/combinat/subset.py index 39aff81e561..7e7cb32b201 100644 --- a/src/sage/combinat/subset.py +++ b/src/sage/combinat/subset.py @@ -41,7 +41,7 @@ from sage.rings.arith import binomial from sage.rings.integer_ring import ZZ from sage.rings.integer import Integer -import choose_nk +import combination ZZ_0 = ZZ.zero() @@ -438,7 +438,7 @@ def rank(self, sub): n = self._s.cardinality() r = sum(binomial(n,i) for i in xrange(len(index_list))) - return r + choose_nk.rank(index_list,n) + return r + combination.rank(index_list,n) def unrank(self, r): """ @@ -467,7 +467,7 @@ def unrank(self, r): r -= bin k += 1 bin = binomial(n,k) - return self.element_class([self._s.unrank(i) for i in choose_nk.from_rank(r, n, k)]) + return self.element_class([self._s.unrank(i) for i in combination.from_rank(r, n, k)]) def __call__(self, el): r""" @@ -769,7 +769,7 @@ def rank(self, sub): raise ValueError("{} is not a subset of length {} of {}".format( sub, self._k, self._s)) - return choose_nk.rank(index_list, n) + return combination.rank(index_list, n) def unrank(self, r): """ @@ -792,7 +792,7 @@ def unrank(self, r): if self._k > n or r >= self.cardinality() or r < 0: raise IndexError("index out of range") else: - return self.element_class([lset[i] for i in choose_nk.from_rank(r, n, self._k)]) + return self.element_class([lset[i] for i in combination.from_rank(r, n, self._k)]) def an_element(self): """ @@ -1346,7 +1346,7 @@ def unrank(self, r): r -= binom k += 1 binom = binomial(n,k) - C = choose_nk.from_rank(r, n, k) + C = combination.from_rank(r, n, k) return self.element_class(sorted([self._s.unrank(i) for i in C])) def _an_element_(self): From ebba4ece62fde88459e50417f233c2c4f5c94263 Mon Sep 17 00:00:00 2001 From: zabrocki Date: Tue, 3 Nov 2015 06:25:27 -0500 Subject: [PATCH 7/8] following Travis's comment replace :1: --- src/sage/combinat/choose_nk.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/sage/combinat/choose_nk.py b/src/sage/combinat/choose_nk.py index 2b0420f483e..285c954b4f9 100644 --- a/src/sage/combinat/choose_nk.py +++ b/src/sage/combinat/choose_nk.py @@ -13,7 +13,7 @@ def rank(comb, n, check=True): sage: import sage.combinat.choose_nk as choose_nk sage: choose_nk.rank((), 3) - doctest:1: DeprecationWarning: choose_nk.rank is deprecated and will be removed. Use combination.rank instead + doctest:...: DeprecationWarning: choose_nk.rank is deprecated and will be removed. Use combination.rank instead See http://trac.sagemath.org/18674 for details. 0 sage: choose_nk.rank((0,), 3) @@ -61,7 +61,7 @@ def from_rank(r, n, k): sage: import sage.combinat.choose_nk as choose_nk sage: choose_nk.from_rank(0,3,0) - doctest:1: DeprecationWarning: choose_nk.from_rank is deprecated and will be removed. Use combination.from_rank instead + doctest:...: DeprecationWarning: choose_nk.from_rank is deprecated and will be removed. Use combination.from_rank instead See http://trac.sagemath.org/18674 for details. () sage: choose_nk.from_rank(0,3,1) From fd5dbe2f3bc3c9443f4d81f658bc1885e854c590 Mon Sep 17 00:00:00 2001 From: zabrocki Date: Wed, 4 Nov 2015 21:02:15 -0500 Subject: [PATCH 8/8] change choose_nk to combination --- src/sage/homology/koszul_complex.py | 2 +- src/sage/rings/polynomial/multi_polynomial_ring_generic.pyx | 4 ++-- src/sage/rings/polynomial/pbori.pyx | 2 +- 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/sage/homology/koszul_complex.py b/src/sage/homology/koszul_complex.py index a5e16aa5e9f..592c2182c5c 100644 --- a/src/sage/homology/koszul_complex.py +++ b/src/sage/homology/koszul_complex.py @@ -14,7 +14,7 @@ from sage.structure.unique_representation import UniqueRepresentation from sage.structure.parent import Parent -from sage.combinat.choose_nk import rank +from sage.combinat.combination import rank from sage.rings.arith import binomial from sage.rings.all import ZZ from sage.matrix.constructor import matrix diff --git a/src/sage/rings/polynomial/multi_polynomial_ring_generic.pyx b/src/sage/rings/polynomial/multi_polynomial_ring_generic.pyx index 773cdebd99b..0991db3ff1e 100644 --- a/src/sage/rings/polynomial/multi_polynomial_ring_generic.pyx +++ b/src/sage/rings/polynomial/multi_polynomial_ring_generic.pyx @@ -640,8 +640,8 @@ cdef class MPolynomialRing_generic(sage.rings.ring.CommutativeRing): We do not check if the provided index/rank is within the allowed range. If it is not an infinite loop will occur. """ - from sage.combinat import choose_nk - comb = choose_nk.from_rank(i, n+d-1, n-1) + from sage.combinat import combination + comb = combination.from_rank(i, n+d-1, n-1) if comb == []: return (d,) monomial = [ comb[0] ] diff --git a/src/sage/rings/polynomial/pbori.pyx b/src/sage/rings/polynomial/pbori.pyx index ab92d9dd498..7f7954c841c 100644 --- a/src/sage/rings/polynomial/pbori.pyx +++ b/src/sage/rings/polynomial/pbori.pyx @@ -1260,7 +1260,7 @@ cdef class BooleanPolynomialRing(MPolynomialRing_generic): [x*y, x*y, x, x, x, x*y, x, y, x*y, 1] """ from sage.rings.integer_ring import ZZ - from sage.combinat.choose_nk import from_rank + from sage.combinat.combination import from_rank t = ZZ.random_element(0,monom_counts[-1]) if t == 0: