7

ハッシュを返すメソッドを持つクラスがあります。通常、次のような結果が得られます。

%resp = $myclass->sub($foo);

次に、返されたハッシュのメンバーに次のようにアクセスします。

$resp{key}{subkey};

2d ハッシュの場合。

これを次のような 1 つのエレガントなラインに組み合わせる方法が必要だと思います。

$myclass->sub($foo)->{key}{subkey}

コードを実行しようとすると Perl がこれを返すため、これは明らかに適切に逆参照されません。

文字列 ("1/8") を HASH ref として使用できません

Perlmonks の「References quick reference」を見て、ランダムな逆参照シーケンスを試してみたところ、Perl は文句を言わないだけでなく、探しているものを返しません。

$%{$myclass->sub($foo)}->{key}{subkey}

これを行うための魔法の逆参照エスケープシーケンスが何であるか誰か教えてもらえますか?

4

5 に答える 5

9

あなたがやろうとしていることは、エレガントでも賢明でもありません。なんとかスカラー コンテキストでルーチンを呼び出すことができました (これが に"1/8"対応します)。

ハッシュ参照を返します。

さて、見てみましょう:

#!/usr/bin/perl

package My::Mine;

use strict; use warnings;

sub test {
    my %h = (
        a => { z => 1},
        b => { y => 2},
    );
    return %h;
}

package main;

use strict; use warnings;

my $class = 'My::Mine';

print { $class->test }->{a}{z}, "\n";

それはうまくいきません。代わりに、次のことを行う必要があります。

print +{ $class->test }->{a}{z}, "\n";

さて、それはエレガントです (違います! ) perldoc -f printを参照してください。

簡単に言うと、ハッシュへの参照を返します。

構築している新しい匿名ハッシュは無料ではないことに注意してください。また、サブルーチンからハッシュをフラット リストとして返すコストもかかりません。

于 2010-02-12T22:03:37.753 に答える
6

サブルーチンを変更してハッシュ参照を返すのが最適ですが、探している機能を取得するには:

{ $myclass->sub($foo) }->{key}{subkey}

によって返されたリストからハッシュ参照を作成し、subすぐに逆参照します

編集:ハッシュ(リストとして)ではなく、サブからハッシュリファレンスを返すことの利点は、主にパフォーマンスの1つです。hashref の場合、ハッシュは一度作成されてからアクセスされます。リストの場合、ハッシュが作成され、リストに変換され、再度作成され、逆参照されます。小さなハッシュの場合、これにはそれほど時間がかかりませんが、大きなハッシュの場合、ランタイムにとって不必要な作業になります。基本的に、ある場所ではデータをリストとして使用し、別の場所ではハッシュとして使用する予定がある場合は、ハッシュをリストとして返すことは問題ありません。ただし、常にハッシュとして使用することを計画している場合は、参照を返す方が明確で高速です。

于 2010-02-12T21:57:54.033 に答える
2

代わりに、サブから HASH 参照を返します。それ以外の場合 (おそらく) ハッシュが LIST に変換され、理由もなく再び HASH に変換されます。

sub mysub() {
  ...
  return \%myhash;
}

参照を返すときに必要なコピーが少ないため、より効率的です。

于 2010-02-12T21:53:29.627 に答える
1

ハッシュの代わりに hashref を返すだけです:

$myclass->sub($foo)->{key}->{subkey}

于 2010-02-12T21:51:57.443 に答える
0

常に 1 つのサブキーだけを取得したい場合は、それを行う短いサブルーチンを作成してください。1 つの利点は、サニティ チェックを簡単に追加できることです。

 sub get_subkey {
      my( $class, $arg, $key, $subkey ) = @_;

      my $hashref = $class->method( $arg );
      return unless ref $hashref;

      return $hashref->{$key}{$subkey};
      }
于 2010-02-13T19:56:01.777 に答える