寻找一种更有效的方法来过滤掉perl哈希

cr8*_*ith 2 perl hash

我的目标是从去除原料堆是记录不是良好的键列表.

我如何以最有效的方式实现这一目标?我目前正在处理的代码感觉拖延.我愿意接受建议.

请注意,这些值可能会变得非常大.

这是我的数据:

# Main data container
my %raw_stack = (
    'a1~a2~a3' => 'dat1~dat2',
    'b1~b2~b3' => 'dat1~dat2',
    'c1~c2~c3' => 'dat1~dat2',
    'd1~d2~d3' => 'dat1~dat2',
    'e1~e2~e3' => 'dat1~dat2',
);

# Container of stack keys only
my @stack_keys = (
    'a1~a2~a3',
    'b1~b2~b3',
    'c1~c2~c3',
    'd1~d2~d3',
    'e1~e2~e3',
);

# Container of valid keys
my @good_keys = (
    'a2',
    'c2',
    'e2',
);
Run Code Online (Sandbox Code Playgroud)

这是我目前正在处理的代码:

foreach my $good_key (@good_keys)
{
    foreach my $stack_key (@stack_keys)
    {
        my @stack = split(/~/, $stack_key);
        if ($stack[1] eq $good_key)
        {

        }
    }
}
Run Code Online (Sandbox Code Playgroud)

我觉得有一种方法,不是需要堆栈键容器.我只是不知道怎么样......

Axe*_*man 8

还有的是,最喜欢的报价由Larry Wall:"在一个关联数组做线性扫描就像是试图俱乐部某人死刑,装载的乌兹."

你应该知道哈希切片.您可以使用它来执行以下操作.当然,这意味着您有一个确切键列表,而您没有.但要说明:

my %clean_hash;
@clean_hash{ @good_keys } = @raw_stack{ @good_keys };
Run Code Online (Sandbox Code Playgroud)

但是,如果您不想复制值,则可以执行更复杂的操作,如下所示:

delete @raw_stack{ grep { $_ !~~ @good_keys } keys %raw_stack };
Run Code Online (Sandbox Code Playgroud)

这使用了5.10的智能匹配.

当然,你必须适应这一点.假设你只是在查看中键[1],它看起来就像你正在寻找一个键中的模式,所以创建一个.

my $regex = join( '|', sort { length( $b ) <=> length( $a ) or $a cmp $b } @good_keys );
$regex    = qr{~($regex)~};
delete @raw_stack{ grep { !m/$regex/ } keys %raw_stack };
Run Code Online (Sandbox Code Playgroud)