0

名前とインデックスが文字列に格納されているハッシュの値を読み取ろうとしています。ハッシュとそのインデックスをハードコーディングした場合にのみ値を取得できますが、別の変数から取得した場合は取得できません。それをよりよく説明するために、以下のコードについて言及しました:

    use strict 'vars';
    #------------------------------

    # Hash to store some values
    our %SystemUser = (
                Username => "system",
                Password => "system"
    );

    # Prints successfully if i use the below technique
    print "Using Hard-Coding technique : ${SystemUser{'Password'}}\n";

    my $Reference = "SystemUser{'Password'}";

    # Doesn't print if i use this technique where $Reference contains the hash-index pair 
    print "Using Referencing technique : ${$Reference}\n";

    print "Reference value : $Reference\n";

SystemUser{'Password'}using ${$Reference}(having $Reference = "SystemUser{'Password'}"value)の値を出力したい

4

3 に答える 3

6

まず第一に、これを技術的なアプローチとして行うことは避けるべきです。

ハッシュのセットの 1 つを名前で動的に取得する必要がある場合、正しい解決策 (Java の世界のパターン) は、ハッシュを hashrefsのハッシュに格納することです。外側のハッシュのキーは、個々のハッシュ名が想定されていたものです。

my %users = (
     SystemUser => {
            Username => "system",
            Password => "system"
     }
    ,GuestUser => {
            Username => "xxx",
            Password => "xxx"
     }

);
print "$users{SystemUser}->{Password}";

技術レベルでは、逆参照構造を使用してそれを行うことができます${$NAME}

ただし、次の点に注意してください。

  • そうするのは悪い習慣です。

    上記のように hashref のハッシュを訴えることができない技術的な理由がない限り、そうしないでください。

  • " use strict" (常に使用する必要があります) の下では、文字列を参照として使用することはまったく許可されていません。

    # WORKS without use strict
    $ perl -e 'our %h=(1=>2); print ${"h"}{1}' 
    
     2
    
    # use strict prohibits that:
    $ perl -e 'use strict; use warnings; our %h=(1=>2); print ${"h"}{1}'
    Can't use string ("h") as a HASH ref while "strict refs" in use 
    
    # but you can unfix by relaxing "strict refs":
    perl -e 'use strict; use warnings; \
        { no strict "refs"; our %h=(1=>2); print ${"h"}{1}; use strict "refs";}'
     2
    
于 2012-08-27T15:09:43.157 に答える
2

${}値自体のみを返すことができます-つまり、ハッシュ、次のペアのインデックスは{}外側にある必要があります。

my $Reference = "SystemUser";
my $Field = 'Password';

print "Reference value : ${$Reference}{$Field}\n";

それでも、名前付き参照によってグローバル変数にアクセスすることは、Perl では悪い習慣です。ハッシュのハッシュを使用する方が良いでしょう。

于 2012-08-27T15:10:42.823 に答える
1

「0ハードコーディング」によってすべてがパラメータ化されていることを意味する場合、実際にはそれを行うことはできません:プログラムは少なくともいくつかの仮定を行う必要があります

しかし、ほとんどのデータを構成可能にすることは実用的ですが、その方法は構成ファイルに Perl コードを保存することではありません。

SystemUser{'Password'}

は Perl コードであり、構成ファイルはデータのみで構成されている必要があります

しかし、たとえば、次のように書くことができます

use strict;
use warnings;

my %config = (
    SystemUser => {
        Username => 'system',
        Password => 'system'
    }
);

while (<DATA>) {
    my ($domain, $field) = split;
    print "Value: $config{$domain}{$field}\n";
}
__DATA__
SystemUser Password

出力

Value: system
于 2012-08-27T15:29:13.183 に答える