2010-06-30 61 views
2

我在Perl中将二维数组引用插入我的堆中。 构建我的堆时应该如何定义'elements'属性以便我可以正确使用我的比较函数?作为一个数组引用在Perl堆中插入数组引用

不能使用字符串(“2.55”),而“严格的裁判”使用...(这意味着我可能真的要:

my $heap = Heap::Simple->new(order  => \&byNumOrStr, 
           elements => [Array => 0] 
          ); 

sub byNumOrStr 
{ 
    my ($a, $b) = @_; 

    $b->[0] <=> $a->[0] #0-th element is a number. 
      || 
    $a->[1] cmp $b->[1]; #1-st element is a number 
} 

我不断收到回这个错误比较我的“数字串”数值)

+0

第1部分(适用于上下文):http://stackoverflow.com/questions/3146484/secondary-order-in-heapsimple/3146526 – Ether 2010-06-30 18:00:36

回答

0

嗯,很可能是$a$b作为字符串传入。尝试在分配后打印出这些变量。

从我可以从文档看,当你通过elements => [ Array => 0 ],除非数组中的第0项是一个数组,那么你就只能在数组的第一个插槽中比较

[Array => $index]
Indicates that the elements are array references, with the key at index $index. So now the element can be not just the key, but also associated data.

这意味着,如果2.55是像数组[2.55,...]那么这是什么东西被传递为$a$b

elements条目告诉H::S你想如何派生密钥。对于一个完全通用的方式,它说你可以通过[Function => $code_ref_for_key]。你可以这样做:

sub first_two_slots { my $ array_ref = shift; return [@ $ array_ref [0,1]]; }

然后用按规定的顺序,它会传递数组到您的订单,并指定

my $heap = Heap::Simple->new(order  => \&byNumOrStr, 
           elements => [Function => \&first_two_slots] 
          ); 

原文评论留在地方:(这不是有关如何Heap::Simple电话订购)。

如果byNumOrStrsort称为请勿在其分配$a$b。这些值由sort设置。如果@_中有某种东西出现,那可能不是你想要的。

+1

无论如何,这些是不同的变量,因为sort的$ a和$ b是包裹可否 – 2010-06-30 17:01:06

+0

@ Leon Timmermans,我认为这不重要。如果他将'$ a'和'$ b'词汇化,那么它们将尝试引用数组,而不是符号表中的引用。 – Axeman 2010-06-30 17:04:34

+1

我不认为'$ a'和'$ b'可以词汇化。 'perldoc perlvar'说:“使用sort()时的特殊包变量,请参阅perlfunc中的”sort“。由于这种特殊性,$ a和$ b不需要声明(使用使用变量或我们的())甚至当使用“strict'vars'”杂注时,如果你希望能够在sort()比较模块或函数中使用它们,请勿用“my $ a”或“my $ b”将它们词汇化。 – Ether 2010-06-30 17:06:15

0

排序一个二维数组并不是真的有意义 - 当你对某物进行排序时,有一个定义的顺序。有两个排序标准并没有使它成为一个二维列表...你的意思是说你有两个元素列表的数据?例如: -

my $element = [ '0', 'string' ]; 

我觉得例1的文档中(“里键和值分开保存”)适用于这里 - 你想引用,而不是值本身进行排序。因此,尝试用 elements => "Any"声明,然后调整自己的排序方法,以匹配:

(我错了..它看起来像elements => [Array => 0]是正确的,因为这些都只是普通的老arrayrefs进行排序。

my $heap = Heap::Simple->new(order  => \&byNumOrStr, 
           elements => [Array => 0], 
          ); 

sub byNumOrStr 
{ 
    my ($val1, $val2) = @_; 

    my $result = 
     $val1->[0] <=> $val2->[0] # the 0th element is a number 
        || 
     $val1->[1] cmp $val2->[1]; # the 1st element is a string 

    # The docs say "this should return a true value if $key1 is smaller than $key2 and a false value otherwise." 
    return $result == -1; 
} 

PS。正如在Secondary Order in Heap::Simple中讨论的那样,Heap :: Simple中的比较函数不需要-1,0或1的返回值,而是true或false。您需要在从函数返回之前转换比较结果。

+0

是的,我的数据是两个元素的列表,或者说是对该列表的引用。 – syker 2010-06-30 18:24:56

+0

此外,为什么你不需要指定返回0? – syker 2010-06-30 18:29:58

+0

@syker:文档说“如果$ key1小于$ key2,则返回一个真值,否则返回一个假值。” - 函数的返回值是评估的最后一个表达式,即与-1的比较。我可以在代码中更清楚一点,我现在要做的。 – Ether 2010-06-30 19:04:53