8

次のスクリプトは、2つの配列のスライスをスマートマッチします。最初は、両方のアレイが同じであり、妥当な結果が得られています。次に、配列の1つを変更し、2つの新しいスライスをスマートマッチングしますが、それでもスライスは同一であると表示されます。ただし、スライスを配列にコピーすると、配列をスマートマッチングすると、実際には異なることがわかります。

スクリプト:

#!/usr/bin/perl
use warnings;
use strict;
use diagnostics;

my @x = qw (one two);
my @y = qw (one two);
my @x_s;
my @y_s;

print "Before change: values are the same:\n";
@x_s = @x[0,1];
@y_s = @y[0,1];
print "\@x_s: @x_s\n";
print +(@x[0,1] ~~ @y[0,1]) ? "equal\n" : "not equal\n";
print +(@x_s ~~ @y_s) ? "equal\n" : "not equal\n";

$x[0]='three';

print "After change: values should be different:\n";
@x_s = @x[0,1];
@y_s = @y[0,1];
print "\@x_s: @x_s\n";
print +(@x[0,1] ~~ @y[0,1]) ? "equal\n" : "not equal\n";
print +(@x_s ~~ @y_s) ? "equal\n" : "not equal\n";

出力:

Before change: values are the same:
@x_s: one two
equal
equal
After change: values should be different:
@x_s: three two
equal
not equal

私はPerl5.10.1を使用していますが、これは配列スライスとハッシュスライスの両方で発生します。なぜこれが起こるのですか?

4

3 に答える 3

5

スマートマッチングは、スライスを使用したスカラーコンテキストで機能するように見えます。

次のコード部分を検討してください。

あなたの場合:

#!/usr/bin/perl

my @foo = (1,2);
my @bar = (3,4);
print @foo[1,2] ~~ @bar[1,2] ? "Equal\n" : "Not equal\n";

それはおそらくあなたが必要とするものです:

#!/usr/bin/perl

my @foo = (1,2);
my @bar = (3,4);
print [ @foo[1,2] ] ~~ [ @bar[1,2] ] ? "Equal\n" : "Not equal\n";
于 2012-02-07T12:34:25.670 に答える
3

スマートマッチ演算子~~は、リストではなく配列に対して魔法をかけます。配列スライスはリストであり、配列ではありません。

アップデート:

スマートマッチは自動的に次の逆参照を行うため、スライスを括弧で囲むだけで解決できます。

print +([@x[0,1]] ~~ [@y[0,1]]) ? "equal\n" : "not equal\n";
于 2012-02-07T12:29:49.810 に答える
0

もともとaskucinsによって投稿されました

そのテストとPerlバージョンの異なる動作に関連するPerlドキュメントでクイッククエリを実行しましたが、これはPerl5.13.5で修正されていることがわかりました。perl5135deltaの「配列スライスに対するスマートマッチング」を参照してください。

以前は、次のコードで一致が成功していました。

my @a = qw(a y0 z);
my @b = qw(a x0 z);
@a[0 .. $#b] ~~ @b;

この奇妙な振る舞いは修正されました[ perl#77468 ]。

于 2016-09-20T22:25:47.493 に答える