performance - 在 Perl 中高效处理所有可能的二维数组组合

标签 performance perl multidimensional-array combinations

我有一个包含数字的二维数组。我正在尝试计算将每个子数组中的一个数字与其他每个子数组中的一个数字相乘的乘积;然后我需要对所有可能的组合执行此操作。

目的是我输入单个事件的频率文件,并获得这些事件的特定系列发生概率的输出,每组有一个事件。

我在上一个问题的帮助下拼凑了一些代码:

for my $aref ( getCartesian(@freq) ) {
    my $p = 1;
    foreach my $n (@$aref) {
        $p = $p * $n;
    }
    print "$p\n";
}


sub getCartesian {
    my @input = @_;
    my @ret = map [$_], @{ shift @input };

    for my $a2 (@input) {
        @ret = map {
            my $v = $_;
            map [@$v, $_], @$a2;
        }
        @ret;
    }
    return @ret;
}

其中@freq是数组的数组,例如:

@freq = [0.1, 0.2, 0.3,]
        [0.4, 0.5, 0.6,]
        [0.7, 0.8, 0.9,]; `and ~ 20 more sub arrays`

这对于一个小的测试文件来说效果很好,但是当我给它我所需的 24 个子数组输入,每个子数组有 3 个项目时,组合的生成显然过于密集,有 3^24 种可能性。 我在一台有 22 GB RAM 的机器上运行它,它在任何输出前 4 分钟后达到最大值。

我的问题是,我如何修改代码,以便我可以为每个组合打印出 $p,而不必在内存中保存整组组合,这会杀死它。我认为时间将是计算的唯一限制因素,而不是资源。

编辑:没有包的基本 Perl 方法会很棒。遗憾的是,我没有 HPC 设施的管理员,

最佳答案

Set::CrossProduct让您遍历笛卡尔积,这样您就不必将所有内容都存储在内存中:

use List::Util qw(reduce);
use Set::CrossProduct;

my @array = (
    [0.1, 0.2, 0.3],
    [0.4, 0.5, 0.6],
    [0.7, 0.8, 0.9]
);

my $iterator = Set::CrossProduct->new(\@array);
while (my $tuple = $iterator->get) {
    say '(', join(', ', @$tuple), '): ', reduce { $a * $b } @$tuple;
}

输出:

(0.1, 0.4, 0.7): 0.028
(0.1, 0.4, 0.8): 0.032
(0.1, 0.4, 0.9): 0.036
(0.1, 0.5, 0.7): 0.035
(0.1, 0.5, 0.8): 0.04
(0.1, 0.5, 0.9): 0.045
(0.1, 0.6, 0.7): 0.042
(0.1, 0.6, 0.8): 0.048
(0.1, 0.6, 0.9): 0.054
(0.2, 0.4, 0.7): 0.056
(0.2, 0.4, 0.8): 0.064
(0.2, 0.4, 0.9): 0.072
(0.2, 0.5, 0.7): 0.07
(0.2, 0.5, 0.8): 0.08
(0.2, 0.5, 0.9): 0.09
(0.2, 0.6, 0.7): 0.084
(0.2, 0.6, 0.8): 0.096
(0.2, 0.6, 0.9): 0.108
(0.3, 0.4, 0.7): 0.084
(0.3, 0.4, 0.8): 0.096
(0.3, 0.4, 0.9): 0.108
(0.3, 0.5, 0.7): 0.105
(0.3, 0.5, 0.8): 0.12
(0.3, 0.5, 0.9): 0.135
(0.3, 0.6, 0.7): 0.126
(0.3, 0.6, 0.8): 0.144
(0.3, 0.6, 0.9): 0.162

关于performance - 在 Perl 中高效处理所有可能的二维数组组合,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21491908/

相关文章:

jquery - 使用 IIS 静态内容服务与从 SQL Server Jquery WCF 获取数据之间的性能差异

c - Perl,我如何为我的 exec'd child 创建一个管道?

c++ - 创建多阵列的任意 View

perl - 是否有一种简单的方法来测试 Moose 属性是否为只读?

regex - 在 shell 脚本中使用正则表达式实现多行模式

c++ - LNK2019 : Unresolved External Symbol . ..函数_main中引用

php - 从多维数组创建 Html 元素

python - python中的快速平方根反比来规范化向量

sql - 加快包含 300k+ 记录的 MySQL 查询

java - CountDiv (Codility) 挑战算法的性能问题