【问题标题】:perl regex - multiple pattern matching, optional matchingperl 正则表达式 - 多种模式匹配,可选匹配
【发布时间】:2010-12-11 01:26:30
【问题描述】:

我被这个正则表达式困住了。它匹配我的 3 个文件名中的 2 个。如果可能,需要帮助获得所有三个。 我还想将扩展名.edu | .net 之前的abc|def|ghiucsb|tech 语言环境名称之一提取到变量中。

如果可能,希望一次性完成。谢谢。

/home/test/abc/.last_run_dir
/home/test/def/.last_file_sent.mail@wolverine.ucsb.edu
/home/test/ghi/.last_file_sent.dp3.tech.net

它没有拿起第一行:

/home/test/abc/.last_run_dir

正则表达式:

$line =~ m#home/test/(\w{3}).*[.](\w+)[.].*#

代码:

my $file = 'Index.lst';
open my $FILE, '<', $file or die "unable to open '$file' for reading: $!";
while (my $line = <$FILE>) {
    chomp($line);
    if ($line =~ m#home/test/(\w{3}).*[.](\w+)[.].*#) {
        open my $file2, '<', $line or die "unable to open '$file' for reading: $!";
        while(my $line2 = <$file2>) {
        print "$line2";
        }
        close $file2;
    }
} #end while
close $FILE;

另外,我如何打印出我可能的匹配项?如果它们是可选的?

【问题讨论】:

    标签: regex perl pattern-matching


    【解决方案1】:

    你可以这样做:

    #!/usr/bin/perl
    use strict;
    use warnings;
    
    while(my $line=<DATA>) {
        chomp($line);
        if ($line =~ m#home/test/(\w{3})/\.(\w+)(?:.*\.(\w+)\.[^.]+)?|$#) {
            print "$line\n";
            print "1=$1\t2=$2\t3=$3\n";
        }
    }
    
    __DATA__
    /home/test/abc/.last_run_dir
    /home/test/def/.last_file_sent.mail@wolverine.ucsb.edu
    /home/test/ghi/.last_file_sent.dp3.tech.net
    

    输出:

    /home/test/abc/.last_run_dir
    1=abc   2=last_run_dir  3=
    /home/test/def/.last_file_sent.mail@wolverine.ucsb.edu
    1=def   2=last_file_sent    3=ucsb
    /home/test/ghi/.last_file_sent.dp3.tech.net
    1=ghi   2=last_file_sent    3=tech
    

    【讨论】:

      【解决方案2】:

      w{3} 之后的正则表达式部分强制它寻找下一个点字点:

      [.](\w+)[.].*
      

      一个简单的解决方法是将此设置为可选。但是当您这样做时,您可能需要先锁定它。*:指定它可以是任何字符串,但 不是 句点。 (顺便说一句,这是一个很好的做法。)

      $line =~ m#home/test/(\w{3})[^.]*([.](\w+)[.].*)?#
      

      编辑:我看到我的解决方案可能需要一些测试来检查正确位置的时间段,仅供参考。

      【讨论】:

      • 我喜欢您提供的解决方案提示:)
      • 谢谢。另外,我如何打印出所有可能的匹配项?包括可选的吗?
      • @jdamae my ( $dir, $dom ) = $line =~ m#home/test/(\w{3})[^.]*([.](\w+)[.].*)?#
      • 伙计们,我还是被卡住了。我试过你的建议。我需要提取我在问题中描述的那些名称。 ucsbtech 或将在 .edu.net 之前获取名称的名称
      • 只是我需要用于文件检查的一个小工具。尝试学习perl。谢谢。
      【解决方案3】:

      您的正则表达式需要两个“.”实例匹配。如果第二个是可选的,请使用 [.]?

      $line =~ m#home/test/(\w{3}).*[.](\w+)[.]?.*#;
      

      【讨论】:

        猜你喜欢
        • 2011-08-04
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多