我试图找出篮子是否有苹果[大问题的简化版]
$check_fruit = "\$fruit =~ \/has\/apple\/";
$fruit="basket/has/mango/";
if ($check_fruit) {
print "apple found\n";
}
check_fruit变量持有评估正则表达式的语句。 然而,check_fruit变量总是变为真,并显示找到的苹果:(
有人可以帮助我吗?如果我错过了什么。
目标: 好的,让我解释一下:
我有一个文件,在每行上定义了一个类似于:
的模式子句Line1: $fruit_origin=~/europe\\/finland/ && $fruit_taste=~/sweet/
Line2: similar stuff that can contain ~10 pattern checks seprated by && or || with metacharacters too
2.我还有一个包含许多此类水果的perl哈希的水果属性列表
3我想对每个水果进行分类,看看有多少水果属于分别由文件的每一行定义的类别。
每行的水果数量/配置文件是否有更简单的方法来实现此目的?非常感谢
答案 0 :(得分:2)
if ($check_fruit)
返回true,因为$ check_fruit是定义的,不是空的而不是零。如果要评估其内容,请使用eval
。但是子程序会更好:
sub check_fruit {
my $fruit = shift;
return $fruit =~ m(has/apple);
}
if (check_fruit($fruit)) {
print "Apple found\n";
}
答案 1 :(得分:0)
为什么需要将语句存储在变量中?如果您确定该值未由用户设置,则可以执行
if (eval $check_fruit) {
但如果用户可以在该表达式中设置任何内容,则这不安全。
答案 2 :(得分:0)
将模式(仅模式)放入变量中,使用匹配分隔符m/.../
的正则表达式中的变量。如果您事先不知道该模式,请使用quotemeta
来转义任何元字符。
它应该是这样的:
my $check_fruit = '/has/apple/'; # here no quotemeta is needed
my $fruit = 'basket/has/mango/';
if ($fruit =~ m/$check_fruit/) {
# do stuff!
}
答案 3 :(得分:0)
$check_fruit
只是一个包含字符串数据的变量。如果要执行它包含的代码,则必须使用eval
。
您的代码中还有一些与字符串引用/转义相关的错误。这也解决了这个问题:
use strict;
use warnings;
my $check_fruit = '$apple =~ m|/has/mango|';
my $apple="basket/has/mango/";
if (eval $check_fruit) {
print "apple found\n";
}
然而,这通常不是一个好的设计。至少,它会使代码混乱。如果$check_fruit
来自用户,这也是一个巨大的安全漏洞。您可以将正则表达式放入变量中,这是更可取的:
编辑:请注意,来自用户输入的正则表达式也可能是一个安全问题,但它的范围更为有限。
my $check_fruit = qr|/has/mango|;
my $apple="basket/has/mango/";
if ($apple =~ /$check_fruit/) {
print "apple found\n";
}
您还可以采取其他措施使您的Perl代码更具动态性。最好的方法取决于你想要完成的任务。