我怎样才能使这个Perl正则表达式工作?

时间:2010-06-10 17:10:50

标签: regex perl

我有这条线

/Od /D "WIN32" /D "_DEBUG" /FD /EHa /MDd /Fo"Debug" /Fd"Debug\vc80.pdb" /W3 /c /Zi /clr /TP .\main.cpp"

我想提取.\main.cpp。我认为以下方法可以解决问题:

if($string =~ /.*\s+(.*)$/i) {
 print "matched ",$1,"\n";
}

因为这个相同的正则表达式在Ruby中工作,并提取我需要的字符串。我怎样才能让它发挥作用?

编辑:这是我设置字符串的方式:

for(find_indexes(\@lines,"/MDd")) {
    my $actual_line = $lines[$_];
    $actual_line    = modify($actual_line,$additional_defs);
}

find_indexes返回与数组ref之后的任何参数匹配的行的索引。 modify sub将返回发送给它的字符串的修改版本,其中包含一些其他定义。

EDIT2:这是modify子:

sub modify {
    my $string      = shift;
    chomp($string);
    my @defines     = @_;
    if($string =~ /.*\s+(\".*?)$/) {
        my $match = $1;
        print "match is $match";
        my $string_copy = $string;
        print "|$string_copy|\n";
    }
}

sub不完整,因为我无法以它应该的方式工作。我在捕获组中添加了一个额外的引号以强制它与名称匹配。虽然发生了一些奇怪的事情,我希望$string_copy的打印能够打印包围在|中的原始字符串。但是,我只获得了领先的管道,而不是结束的管道。我想也许Perl正在解释内插变量错误,我试着这样做:

print "|",$string_copy,"|\n";

但我仍然只得到一个领先的管道。这让我觉得字符串可能确实有问题。我想不出别的什么。

4 个答案:

答案 0 :(得分:2)

my $string = '/Od /D "WIN32" /D "_DEBUG" /FD /EHa /MDd /Fo"Debug" /Fd"Debug\vc80.pdb" /W3 /c /Zi /clr /TP .\main.cpp"';
if($string =~ /.*\s+(.*)$/i) {
    print "matched ",$1,"\n";
}

这适用于我并打印matched .\main.cpp"

请说明如何设置$string。你可能会用引号或其他东西搞砸了。

编辑:您的字符串末尾是否有\x0d符号?打印字符串时,您不会在日志中注意到它,chomp不会将其删除:

my $string = '/Od /D "WIN32" /D "_DEBUG" /FD /EHa /MDd /Fo"Debug" /Fd"Debug\vc80.pdb" /W3 /c /Zi /clr /TP .\main.cpp"' . "\x0d";
chomp $string;
if($string =~ /.*\s+(.*)$/i) {
    print "matched ",$1,"\n";
}

这为我打印matched,而不捕获文件名。也许那是你的情况?

C:\>perl --version

This is perl, v5.10.1 built for MSWin32-x64-multi-thread

答案 1 :(得分:2)

前导.*没有意义,/i修饰符也是如此。

如果字符串以换行符结尾,则会与\s+匹配。由于后面的(.*)无法匹配,因此匹配将成功,但$1将为空。相反,强制它匹配某些内容:/(\S+)"$/

答案 2 :(得分:1)

看起来你想要的只是

$string =~ /(\S+)$/

答案 3 :(得分:0)

试试这个:

#!/usr/bin/perl

$string = <STDIN>;
chomp($string);
print $string;

if($string =~ /.*\s+(.*)$/) {
  print "\nmatched ",$1,"\n";
}

这是为i486-linux-gnu-thread-multi构建的perl,v5.8.8