perl/reference/hash

思うところあってハッシュの使い方とリファレンスについて復習中.
C/C++をやっていたのでリファレンスの考え方自体はわかるのだが,それをどう書くかが良くわかっていない.ということで,多重ハッシュのリファレンス操作のサンプルコードを書いてみたのでのせておく.
参考

サンプルコード(参照 : コードは ハッシュのハッシュ からもらってきてます)

#!/usr/bin/perl -w
use strict;

my %drink=(
           cool => {orange => "100",
                    coffee => "120",
                    cola => "140",
                   },
           hot => {tea => "100",
                   coffee => "120",
                  },
          );
my $dref = \%drink;

print "# use \%drink\n";
foreach my $item (keys %drink) {
  print "$item\n";
  foreach my $item2 (keys %{$drink{$item}}) {
    print "    $item2 = $drink{$item}{$item2}\n";
  }
}
print "\n# use \$dref\n";
foreach my $item (keys %$dref) {
  print "$item\n";
  foreach my $item2 (keys %{$$dref{$item}}) {
    print "    $item2 = $$dref{$item}{$item2}\n";
  }
}

print "\n# check\n";

print $dref, "\n";
print \%drink, "\n";

print %$dref, "\n";
print %drink, "\n";

print $$dref{cool}, $$dref{hot}, "\n";
print $drink{cool}, $drink{hot}, "\n";

print %{$$dref{cool}}, %{$$dref{hot}}, "\n";
print %{$drink{cool}}, %{$drink{hot}}, "\n";

print $$dref{cool}{cola}, "\n";
print $drink{cool}{cola}, "\n";

実行結果

$ perl hashtest.pl
# use %drink
cool
    cola = 140
    coffee = 120
    orange = 100
hot
    coffee = 120
    tea = 100

# use $dref
cool
    cola = 140
    coffee = 120
    orange = 100
hot
    coffee = 120
    tea = 100

# check
HASH(0x1002f17c)
HASH(0x1002f17c)
coolHASH(0x10010ec0)hotHASH(0x1002fa70)
coolHASH(0x10010ec0)hotHASH(0x1002fa70)
HASH(0x10010ec0)HASH(0x1002fa70)
HASH(0x10010ec0)HASH(0x1002fa70)
cola140coffee120orange100coffee120tea100
cola140coffee120orange100coffee120tea100
140
140                                          

見た目わかりにくいけどもう面倒なので放置.

図にするとこんな感じか.

   $dref
  +---------+        %drink
  | \%drink |------> %$dref
  +---------+       +------------------+
               cool | \%{$drink{cool}} |--------> %{$drink{cool}}
                    | \%{$$dref{cool}} |          %{$$dref{cool}}
                    +------------------+         +----------------------------+
               hot  | \%{$drink{hot}}  |    cola | 140 = $drink{cool}{cola}   |
                    | \%{$$dref{hot}}  |         |     = $$dref{cool}{cola}   |
                    +------------------+         +----------------------------+
                                          coffee | 120 = $drink{cool}{coffee} |
                                                 |     = $$dref{cool}{coffee} |
                                                 +----------------------------+
                                          orange | 100 = $drink{cool}{orange} |
                                                 |     = $$dref{cool}{orange} |
                                                 +----------------------------+

アロー演算子('->')は見づらくなるので嫌い.嫌いというか C/C++ 時代の悪夢がよみがえるので使わない方向で行きたい.