【问题标题】:All possible lists of pairs from two lists来自两个列表的所有可能的对列表
【发布时间】:2011-04-18 21:13:04
【问题描述】:

假设我有两个项目列表。这两个列表的长度可能相同,也可能不同。

如何生成所有可能的项目对的所有列表,其中一对由每个列表中的一个项目组成?每个项目只能成对。

所以,如果一个列表是:

(1, 2, 3)

另一个列表是:

(a, b)

那么所有可能对的列表将是:

(1a, 2b)
(1a, 3b)
(1b, 2a)
(1b, 3a)
(2a, 3b)
(2b, 3a)

(我在 Perl 中实现了这一点,但显然算法是重要的部分。)

提前致谢。我的递归 foo 不起作用!

【问题讨论】:

  • 那些不是成对的,它们是成对的。您的问题描述与您的预期输出不符!
  • @Robin Green:实际上,它似乎是所有可能配对的列表。换句话说,它列出了所有可能的一对一功能。
  • 糟糕,抱歉,我误会了。现在说得通了。
  • 谢谢。你是对的 - 标题是垃圾,一些描述也是如此。我现在试着让它更清楚一点。当然,它们实际上是成对的列表,而不是成对的成对。它们只是上面的一对,因为在这个简单的示例中,第二个列表只有两个项目。再次感谢。

标签: algorithm recursion combinations


【解决方案1】:

这里是示例代码。

use strict;
use warnings;

sub unordered_pairs {
    return if @_ < 2;
    my $first = shift;
    return (map [$first, $_], @_), unordered_pairs(@_);
}

sub cartesian_product {
    my @answers = [];
    for my $list (@_) {
        @answers = map {
            my $value = $_;
            map [@$_, $value], @answers
        } @$list;
    }
    return @answers;
}

sub possible_pairs_of_pairs {
    my ($list1, $list2) = @_;

    my @pairs1 = unordered_pairs(@$list1);
    my @pairs2 = unordered_pairs(@$list2);

    return map {
        [[$_->[0][0], $_->[1][0]], [$_->[0][1], $_->[1][1]]],
        [[$_->[0][0], $_->[1][1]], [$_->[0][1], $_->[1][0]]],
    } cartesian_product(\@pairs1, \@pairs2);
}

及示例用法:

use Data::Dumper;
my @stuff = possible_pairs_of_pairs([1, 2, 3], ['a', 'b']);
print Dumper(\@stuff);

请注意,如果您的列表包含 $n$m 元素,则最终输出将包含 $n * ($n-1) * $m * ($m-1) / 2 元素。这将在更大的列表中迅速爆发。阅读http://perl.plover.com/Stream/stream.html 以获取有关如何使用这种数据结构不耗尽内存的灵感。 (或者阅读Higher Order Perl,最终出自那篇文章的书。)

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-04-04
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-11-22
    • 2022-01-12
    • 2016-07-10
    • 1970-01-01
    相关资源
    最近更新 更多