Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/362.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 计算具有多重性且无顺序的集合分区的计数_Python_Combinatorics - Fatal编程技术网

Python 计算具有多重性且无顺序的集合分区的计数

Python 计算具有多重性且无顺序的集合分区的计数,python,combinatorics,Python,Combinatorics,我有一段代码可以计算一组(可能重复的)整数的分区。但我感兴趣的是一组可能的划分和多重性 例如,您可以启动以下代码: import numpy as np from collections import Counter import pandas as pd def _B(i): # for a given multiindex i, we defined _B(i) as the set of integers containg i_j times the number j:

我有一段代码可以计算一组(可能重复的)整数的分区。但我感兴趣的是一组可能的划分和多重性

例如,您可以启动以下代码:

import numpy as np
from collections import Counter
import pandas as pd

def _B(i):
    # for a given multiindex i, we defined _B(i) as the set of integers containg i_j times the number j:
    if len(i) != 1:
        B = []
        for j in range(len(i)):
            B.extend(i[j]*[j])
    else:
        B = i*[0]
    return B

def _partition(collection):
    # from here: https://stackoverflow.com/a/62532969/8425270
    if len(collection) == 1:
        yield (collection,)
        return
    first = collection[0]
    for smaller in _partition(collection[1:]):
        # insert `first` in each of the subpartition's subsets
        for n, subset in enumerate(smaller):
            yield smaller[:n] + ((first,) + subset,) + smaller[n + 1 :]
        # put `first` in its own subset
        yield ((first,),) + smaller

def to_list(tpl):
    # the final hierarchy is
    return list(list(i) if isinstance(i, tuple) else i for i in tpl)


def _Pi(inst_B):
    # inst_B must be a tuple
    if type(inst_B) != tuple :
        inst_B = tuple(inst_B)
    pp = [tuple(sorted(p)) for p in _partition(inst_B)]
    c = Counter(pp)
    Pi = c.keys()
    N = list()
    for pi in Pi:
        N.append(c[pi])
    Pi = [to_list(pi) for pi in Pi]
    return Pi, N


if __name__ == "__main__":

    import cProfile
    pr = cProfile.Profile()
    pr.enable()
    sh = (3, 3, 3)
    rez = list()
    rez_sorted= list()
    rez_ref = list()
    for idx in np.ndindex(sh):
        if sum(idx) > 0:
            print(idx)
            Pi, N = _Pi(_B(idx))
            print(pd.DataFrame({'Pi': Pi, 'N': N * np.array([np.math.factorial(len(pi) - 1) for pi in Pi])}))
    pr.disable()
    # after your program ends
    pr.print_stats(sort="tottime")
这段代码为整数元组的几个示例(由
np.ndindex
生成)计算我需要的分区和计数。一切都发生在
\u分区
\u Pi
函数中,这是您应该看到的

如果您仔细观察这两个函数是如何工作的,您将看到它们计算每个潜在分区,然后计算它们出现的次数。对于小问题,这很好,但是如果prolbme的大小增加,这将开始花费大量的时间。试着设置
sh=(5,5,5)
,你就会明白我的意思

因此,问题如下:

有没有办法直接计算分区,而不是计算发生的次数?

编辑:我在mathoverflow上交叉发布,他们在corrolary 2.10(pdf第10页)中提出了一个解决方案。这一问题可以通过在这个迭代中实现集合p(v,r)来解决

我希望,就像在单变量情况下一样,这些集合会有一个很好的递归表达式,但我还没有找到


更多编辑:这个问题相当于查找多集的所有(多集)分区。如果一个集合的(集合)划分的解决方案是由贝尔部分多项式给出的,那么这里我们需要这些多项式的多元版本。

为了确保我理解:元组(0,1,2)意味着“0”的0个副本,“1”的1个副本和“2”的2个副本?在这种情况下,分区的数量是4?是的,您理解正确!正如我的代码输出所示,有4个可能的分区,在本例中,两个分区的重数为1,两个分区的重数为2。对于更高的问题,这些多重性加起来会让我的速度慢很多。你所描述的问题被称为多重集的划分。我找不到一个好的解决方案,但在不同的地方有很多关于它的参考文献。例如,看这里:是的,这不是完全相同的事情,因为那里的多集是非常特殊的,他们找到了一个不适用于我的解决方案;但事实上,这是我的问题。显然,这是一个难题。如果我可以问-用例是什么?为了确保我理解:元组(0,1,2)表示0个“0”副本、“1”副本和2个“2”副本?在这种情况下,分区的数量是4?是的,您理解正确!正如我的代码输出所示,有4个可能的分区,在本例中,两个分区的重数为1,两个分区的重数为2。对于更高的问题,这些多重性加起来会让我的速度慢很多。你所描述的问题被称为多重集的划分。我找不到一个好的解决方案,但在不同的地方有很多关于它的参考文献。例如,看这里:是的,这不是完全相同的事情,因为那里的多集是非常特殊的,他们找到了一个不适用于我的解决方案;但事实上,这是我的问题。显然,这是一个难题。如果我可以问一下,用例是什么?