【问题标题】:How to optimise storage size and performance when generating a large list of sequences in python?在 python 中生成大量序列时如何优化存储大小和性能?
【发布时间】:2017-09-13 23:25:19
【问题描述】:

问题

对于给定的整数 n,我正在生成这种形式的所有可能序列:

  • 序列长度为n
  • 对于某些k < n,该序列必须包含数字nn-1n-2...n-k ≥ 1。数字可以重复。

例如,对于n = 3,可能的序列是:

1, 2, 3
1, 3, 2
2, 1, 3
2, 3, 1
3, 1, 2
3, 2, 1
2, 2, 3
2, 3, 2
3, 2, 2
2, 3, 3
3, 2, 3
3, 3, 2
3, 3, 3

换句话说,序列必须包含n 和从n 开始倒数的数字,没有任何跳转,但没有特定的顺序,并且允许重复。

给定n,此类序列的数量由ordered Bell numbers 或 Fubini 数给出,它们增长得非常快。

这是我用来生成序列的代码:

from sympy.utilities.iterables import multiset_permutations

def generate_sequences(n):
    sequences = []
    for unpermuted_seq in unpermuted_sequences(n,n):
        for permutation in multiset_permutations(unpermuted_seq):
            sequences.append(permutation)
    return sequences

def unpermuted_sequences(number,remaining_slots):
# Generates list of possible unpermuted sequences 
    if remaining_slots == 0:
        yield []
        return
    for repetitions in range(1, remaining_slots + 1):
        for sequence in unpermuted_sequences(number - 1, remaining_slots - repetitions):
            yield sequence + repetitions*[number]

问题

上面发布的代码按预期工作。我主要担心以下两个问题:

  1. 存储: 对于我的特定应用程序,一旦选择了n,我需要存储所有序列。我最终将需要遍历列表并删除不满足特定条件的序列。但是,即使对于较小的n(即n > 8),也需要大量内存(GB 的顺序)。

  2. 生成时间:我的代码需要很长时间才能生成序列,即使是小的n

如何以优化存储和生成时间的方式生成序列?

【问题讨论】:

  • 最好的选择当然是只生成满足条件的序列,而不是生成以后要丢弃的序列。你能告诉我们条件是什么吗?
  • 你看过 itertools 吗? docs.python.org/3/library/itertools.html
  • @m69:这种情况无法提前知道,因为它是基于后来的观察
  • @robert king:我查看了 itertools,但它似乎没有多重排列

标签: python algorithm performance optimization storage


【解决方案1】:

我当然会将这些值存储为二进制。对于高达 16 的数字,您甚至可以使用半字节(4 位 - 使用一些位移位)来存储每个值。因此,对于n=8,您“只”需要 545835 * 4 个字节 = ± 2MB -- 对于n=10 ± 500MB。

为了更快地处理和写入文件,您可以使用memory mapping(预先计算所需大小,创建该大小的文件,并使用内存映射打开它)。

这样每个值都可以直接写入映射(即文件,就好像它是内存一样),这也将消除较慢的sequences.append(permutation)。还可以考虑只编写您需要的序列,因为如果您想稍后删除它们,您需要移动所有其他数据。

您还可以在文件中添加一个带有一些值的小标题:nknumber of sequences,二进制。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-03-19
    • 2012-09-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多