• ベストアンサー
※ ChatGPTを利用し、要約された質問です(原文:PerlでHashのキーを制限したい)

PerlでHashのキーを制限する方法

tsuduki123の回答

回答No.1

どうしてもという場合には lvalue を使いますかねぇ? あんまり使ったことないので自信はないです。 個人的なおすすめは配列にして普通に変数でアクセスですね。 以下はlvalueのサンプルです #!/usr/bin/env perl use strict; use warnings; package SAMPLE; { sub new() { my $prot = shift || 'SAMPLE'; return bless { 'MA' => 0 , 'MB' => 0 },$prot; } sub MA : lvalue { shift->{'MA'}; } sub MB : lvalue { shift->{'MB'}; } } package main; my $sample = SAMPLE->new(); $sample->MA = 5; printf "MA:%d, MB:%d\n", $sample->MA, $sample->MB; $sample->MC = 5; exit 0

aki04
質問者

お礼

lvalue というのは初めて知りました。Perl は色々ありますね… ありがとうございます。 やっぱり配列ですか。 Perl歴が浅いので他の人はどうしている/どうするのかとか参考になります。 ただ引数が多い場合、配列だとうっかり順番が違ってても気づきにくいんじゃないかと気になるんですよね… みなさんのソースを見つつ自分でも色々考えていたのですが、 キー値を定数定義してそれを使うようにしたらどうかと思いました。 どうなんだろう… 一応定義していない定数(typo)を使おうとすると use strict; で怒ってもらえるけど… 一応貼っておきます。 { package MyUtil;   use constant KEY_FOO_ID => 'id';   use constant KEY_FOO_NAME => 'name';   sub foo {     my ($args) = @_;     print "id[" . $args->{MyUtil::KEY_FOO_ID} . "] ";     print "name[" . $args->{MyUtil::KEY_FOO_NAME} . "] ";   } } sub test {   # ハッシュに値を詰める   my $hsref = {     MyUtil::KEY_FOO_ID => '01', ##   MyUtil::KEY_FOO_NAMO => 'SUZUKI', # error     MyUtil::KEY_FOO_NAME => 'YAMADA'   };   # 関数に渡す   MyUtil::foo($hsref); } #test();

関連するQ&A

  • Perlでexecuteをまとめて実行したい

    以前似たような質問をしたモノですが、 Perl(cgi)ファイルからテーブル内の一定の項目をDELETEしようとしています 具体的にいうと、多数あるチェックボックスにチェックされた項目のみを削除するプログラムで、チェックされた値はハッシュに格納し読み込み、削除をしています。 foreach $key (keys %hash) {   # 取り出した値を$noに代入   $no = $hash{$key};   # SQL発行   $sql = $db->prepare("DELETE FROM テーブル名 WHERE レコード指定名='$no'");   # SQL実行   $sql->execute; } もしくは # ハッシュに入れた値をカウント $n = keys( %hash ); # プレースホルダを使用し削除の実行 $sql = $db->prepare("DELETE FROM テーブル名 WHERE レコード指定名=?"); for($i=0; $i<$n; $i++) {    # SQL実行    $sql->execute(@hash{$i}); } 上記の方法でどちらも問題なく実行できているのですが、ご覧のようにハッシュに格納されている数だけ$sql->execute;を実行しているため効率が悪い、と担当者から指摘をうけました。 少しでもマシンの負担を軽くし、スムーズにするためにexecuteをまとめて実行することを求められています。 selectcol_arrayref などを使う方法などを検索できたのですが、具体的なサンプルがないとまだ分からない初心者で、上記のプログラムに当てはめる方法が分からないでいます。 ご教授のほどよろしくお願いします。

    • ベストアンサー
    • MySQL
  • Perlの関数の引数について詳細

    perlで引数に関することでわからないことがあるのですが、以下の状態で、実行した際に、$aは1が入るのはわかりますが、$bには具体的にどんな値が入っているのでしょうか? 引数が無い場合は、デフォルトで1をセットしたいです。 phpのvar_dump関数のようなものがPerlには存在すれば便利ですが、そういうものはあるのでしょうか? sub test{ my ($a, $b, $c, $d) = @_; } &test(1); あと引数の数を2つは必須にして、残りの引数(3つ目はデフォルトで1つ目の引数と同じ値になり、4つ目以降はデフォルトで1となる 関数のプロトタイプを書きたいのですが、どうですればよいのでしょうか? sub test($$;@  ?のようなものを見たことがあるのですが、どんな意味をしているのでしょうか?結構複雑な引数を持たせることができそうなのですが、詳しく書かれている本などご存知の方教えてください。

    • ベストアンサー
    • Perl
  • 【javascript】ハッシュのキーをソートして取り出したい

    ハッシュのキーをソートして取り出したいです。 perlで表現すると、以下の様なかんじです。 foreach $key (sort keys %hash) { ... } そこで、prototype.jsを使って以下の様に書いてみました。 <html> <head> <script type="text/javascript" src="prototype.js"></script> </head> <body > <script > var table = {c:'C', b:'B', a:'A'}; $H(table).keys().sort().each(function(key){ alert(key + ' ' + table[key]); }); </script> </body> </html> 他に良い方法ありましたら、教えてください。

  • perlのeach関数の動き?

    perl5.8ですがeach関数を使って何回か動かすと、ハッシュ内にあるはずのデータが取得できなくなります。 my %hash = ('a'=>100, 'b'=>50); for(1..100){ while( my ($k, $v) = each %hash ){ if($k eq 'a'){ ... 通過しなくなる。 } } } PHPでは、配列に対してですが、reset関数というものがありますが perlでは、何か対策でもあるのでしょうか? 現在は、keys関数で代用しています。 eachでループは無理なのでしょうか?

    • ベストアンサー
    • Perl
  • ハッシュの中身の表示

    ハッシュの中身の確認ができなくて困っています。 下記のような実行文においてです。 当然、test の戻り値は、スカラーとハッシュです。ハッシュを戻すときには参照渡し記号の\もつけています。 my ($return_code, %hash_data) = test(); 表示しようとすると、 Hash(0x5b04) のような表示にしかなりません、、 (試した表示方法は、下記4つです。) (環境は、WindowsXP上での、ActivePerl-5.10.0.1004 です。) foreach $key ( keys( %Hash ) ) { print "キー値 : $key\n"; print "値 : $Hash{$key} \n " } while ( ( $key , $value ) = each %Hash ){ print "キー値 : $key\n"; print "値 : $value \n " ; } use Data::Dump qw(dump); print dump(\%hash); #print %display_test; 宜しくお願いします。

    • ベストアンサー
    • Perl
  • Perl(cgi)ファイルからMySqlで管理しているデータベース制御に関して質問

    Perl(cgi)ファイルからテーブル内の一定の項目をDELETEしようとしています ランダムに選択させる値をハッシュに格納し読み込み、削除を試みています。 foreach $key (keys %hash) { # 取り出した値を$noに代入 $no = $hash{$key}; # SQL発行 $sql = $db->prepare("DELETE FROM テーブル名 WHERE レコード指定名='$no'"); # SQL実行 $sql->execute; } 上記の方法で問題なく実行できているのですが、ご覧のようにハッシュに格納されている数だけSPQを実行しているため効率が悪い、と 担当者から指摘をうけました。 PHPであればSPQの実行あと、for文で『 レコード指定名='_no'』の部分だけをループさせることができたのですが Perlではうまくいきません。ご教授ください。よろしくお願いします。 ちなみにPerlをはじめとしてプログラムそのものを勉強し始めて1ヶ月の初心者です。

    • ベストアンサー
    • MySQL
  • C言語 関数プロトタイプ宣言の引数に配列を入れたいのですが

    関数プロトタイプ宣言(自作関数)の引数に、A[4][4]というような配列を入れたいのですが、コンパイル時にエラーでincompatibleといわれてしまいます。 A[0][0]からA[3][3]までを個別に引数に指定してもエラーになります。 良い方法は無いでしょうか?

  • 静的ハッシュの配列のキーに対応する値の数の多さ順で表示させたい

    ハッシュのキーに対応する値の数の多さ順で表示させたいと考え、下記の所まで試行錯誤しておりますが、どうにも思ったようにソートできずにおります。 #!/usr/bin/perl use strict; my(%a, $i, $j ,$allarray ,@keys ,@keys2 ,%hash ,%files ,$a_mumei_ref ,$key ,$value ,@value ,$x ,$files); # ハッシュの配列を静的に作る %a = ( '0' => [ qw(0) ], '1' => [ qw(1 1) ], '3' => [ qw(3 3 3) ], '7' => [ qw(7 7 7) ], '2' => [ qw(2) ], '4' => [ qw() ], '5' => [ qw() ], '6' => [ qw() ], '8' => [ qw(8 8) ], '9' => [ qw(9) ], ); @keys = sort { $hash{$b} <=> $hash{$a} || length($b) <=> length($a) || $a cmp $b } keys %a; #ハッシュのキーを数字順で表示 foreach (@keys){ print $_ ."\n"; } # 静的に作ったハッシュの配列を取り出してみる foreach $i (sort keys %a) { for ($j = 0; $j <= scalar(@{$a{$i}})-1; $j++) { print '$a{'. $i. '}['. $j. ']='. $a{$i}[$j]. ' '; } $allarray=scalar(@{$a{$i}})-1; print "No$i:kosuu:$allarray"; print "\n"; #配列の値の個数を調べその配列を作成 my($a_mumei) = $allarray; $a_mumei_ref = \$a_mumei; $files{"$i"}=($i,$a_mumei_ref); } #each関数で%filesの中身を表示 while ( ( $key , $value ) = each %files ){ print "key:$key value:$$value\n" ; } #試行錯誤 foreach $x (sort { $files{$b} <=> $files{$a} } keys %files){ print "$x => $files->{$x}\n"; } @keys2 = sort {$hash{$a} <=> $hash{$b}} keys %files; #@keys2 = sort { $hash{$b} <=> $hash{$a} || length($b) <=> length($a) || $a cmp $b } keys %files; #@keys2 = sort { $hash{$a} cmp $hash{$b} } keys %files; print "@keys2\n"; print "\n"; __END__; 私のイメージしておりますのは、ソートした結果がハッシュのキーに対応する値の数の多さ順で下記のように表示させたいのですが、 どのようにすれば可能でございますか、ご教授願えませんでしょうか key:3 value:2・・・この場合valueは配列の個数 key:7 value:2 key:8 value:1 key:1 value:1 key:9 value:0 key:2 value:0 key:0 value:0 key:6 value:-1 key:4 value:-1 key:5 value:-1

    • ベストアンサー
    • Perl
  • ハッシュリファレンスの無名変数

    サブルーチンにハッシュリファレンスを渡すために、 以下のようにすると上手く実行されます。 %hash = ( baa => 1, boo => 2 ); test(\%hash); sub test { my %hash = %{shift}; print $hash{baa}; } これを、%hashに格納せずに、 直接渡そうとすると上手くいきません。 test(\( baa => 1, boo => 2 )); 考え方が間違っているのでしょうか。

    • ベストアンサー
    • Perl
  • perl 配列名変数指定するには

    perlプログラムで for文で ループ分の配列定義するには どうしたらよいですか? 下記のようなことができないかと 考えております。 for(my $i = 0; $i < $file_no; $i++){ my @{"segments$i"} =(); #配列定義 my ${"line$i"}="";     #変数定義 my %{"hash$i"}= ();    #ハッシュ定義 open(ARG1,$ARGV[$i]); while(<ARG1>){ ${'line'.$i} = $_; chomp ${'line'.$i}; @{'segments'.$i} = split(/\t/,${'line'.$i});        ${'hash'.$i}{${'segments'.$i}[0]}=${'segments'.$i}[1];     } close(ARG1); } #下記で、その後 各ハッシュに設定したデータをもとに いろいろ計算したい foreach my $a (keys %{'hash'.$i}){ ・・・ } 今は、Can't declare array dereference in "my" at test.pl line XX, near "} =" と 配列定義でエラーとなり処理できません。

    • ベストアンサー
    • Perl