スカラー データ以外のものを Perl 変数に格納するときはいつでも、オブジェクト指向の Perl について考え始める必要があります。
Perl Object Oriented Tutorialを見てください。
私はあなたのここですべてのオブジェクト指向に行きます:
#! /usr/bin/env perl
use strict;
use warnings;
my %list;
my $list{1} = Widget->new("first", 2);
my $list{2} = Widget->new("second", 3);
my $i = "2";
check_something( $list{$i} );
わお!私が何をしているのかは明らかです。%list
ウィジェットのオブジェクトを含むハッシュが呼び出されました! サブルーチンcheck_somthing
が Widget オブジェクトを取得しています。$list{$i}
それは引数としてあるはずです。
しかし、ウィジェットはどのように見えますか:
package Widget;
sub new {
my $class = shift;
my $self = shift;
my $name = shift;
my $quantity = shift;
my $self = {};
bless $self, $class;
$self->Name($name) if defined $name;
$self->Quantity($quantity) if defined $quantity;
return $self;
}
sub name {
my $self = shift;
my $name = shift;
if ( defined $name ) {
$self->{name} = $name;
}
return $self->{name};
}
sub Quantity {
my $self = shift;
my $quanity = shift;
if ( defined $quanity ) {
$self->{quantity} = $quantity;
}
return $self->{quantity};
}
それはとても簡単です。ハッシュのハッシュの代わりにオブジェクトを使用することで、ロジックを簡素化しました。サブルーチンに渡したいものが Widget オブジェクトであることは簡単にわかります。実際、check_somthing
サブルーチンは別のメソッドである可能性があります。
sub check_something {
my $widget = shift;
my $name = $widget->Name;
my $quanity = $widget->Quantity;
# Here be dragons...
return ???
}
今、私のコードは次のようになります。
#! /usr/bin/env perl
use strict;
use warnings;
my %list;
my $list{1} = Widget->new("first", 2);
my $list{2} = Widget->new("second", 3);
my $i = "2";
$list{$i}->check_something;
これにより、コードを改善する多くのことが行われることに注意してください。
- まず、ロジックをクリーンアップします。リストのハッシュやハッシュ、または理解するのが難しい構造を渡しているわけではありません。おそらく、あきらめてここで質問する前に、理解するのに2〜3時間無駄にしました。(犯罪はありません。私はそこに行って、自分でやったことがあります)。代わりに、理解しやすいオブジェクトを渡しています。
- 次に、
check_something
サブルーチンがウィジェットでのみ使用できるようにします。Widget 以外のオブジェクトを に渡そうとするcheck_something
と、失敗します。さらに良いことに、別のオブジェクトWooble
を独自のcheck_something
サブルーチンで呼び出すことができ、Perl は私が実際に何をチェックしているかを判断します。
例えば:
my $widget = Widget->new("first", 2);
my $wooble = Wooble->new(1, "slam");
$widget->check_something;
$wooble->check_something;
Widgets と Woobles には独自のcheck_something
メソッドがあり、Perl は、どのオブジェクトがWidgetで、どのオブジェクトがWoobleであるかを認識しているため、実行する必要があるものを認識していcheck_something
ます。
- 最後に、
use strict;
もう壊れていません。プラグマはエラーのuse strict;
90% をキャッチします。ただし、これらの複雑な構造を未加工のコードから切り出して作成すると、キャッチできてuse strict;
もキャッチできない同じ時間のエラーが発生する可能性があります。
例えば:
%list = (
1 => {name => 'first', quantity => 2},
2 => {name => 'second', quanity => 3}
);
エラーが表示されますか? 私は一方を使用quantity
しましたが、もう一方はスペルquanity
を間違えました。このタイプのエラーは、コンパイラによってキャッチされません。でも:
$list{1} = Widget->new;
$list{1}->name('first');
$list{1}->quantity(2);
$list{2} = Widget->new;
$list{2}->name('second');
$list{2}->quanity(3); #Compiler Error!
これで、Perl コンパイラは私のエラーをキャッチします。これquanity
は、単にハッシュ参照へのキーではなく、存在しないサブルーチンであるためです。
他の人はすでに技術的に正しい答えを与えていますが、ハッシュのハッシュ、リストのハッシュ、またはハッシュのリストなどの複雑なデータ構造を定期的に使用する場合は、オブジェクトの操作を開始するときが来ました。それらに慣れると、フラストレーションやロジックの問題が少なくなり、はるかに高速にコーディングできることがわかります。