【问题标题】:Perl regex splitting with nested commasPerl 正则表达式用嵌套逗号分割
【发布时间】:2014-02-18 23:07:43
【问题描述】:

我有一个键值对字符串,其中的对以逗号分隔,但值有嵌套的逗号。

例如

"key1|val1,key2|val2_a,val2_b,val2_c,key3|val3"

我想把它分解成一个散列并用以下内容破解它:

my $str = "key1|val1,key2|val2_a,val2_b,val2_c,key3|val3";
my @vars = split(/([^,\s]+)\|/ ,$str);
my @arr = splice @vars, 1;
my %hash  = @arr;
print Dumper(\%hash);

这给了我:

$VAR1 = {
      'key2' => 'val2_a,val2_b,val2_c,',
      'key1' => 'val1,',
      'key3' => 'val3'
    };

我正在寻找一种更优雅的方式来执行此操作。我认为它可以用一个正则表达式来完成,但我很难弄清楚。谁能指出我正确的方向?

【问题讨论】:

    标签: regex perl


    【解决方案1】:

    尝试在拆分中使用积极的前瞻。

    #!/bin/perl
    
    use strict;
    use warnings;
    use Data::Dumper;
    
    my $str = "key1|val1,key2|val2_a,val2_b,val2_c,key3|val3";
    my %hash = split(/\||,(?=\w+\|)/, $str);
    
    print Dumper(\%hash);
    

    输出:

    $VAR1 = {
              'key2' => 'val2_a,val2_b,val2_c',
              'key1' => 'val1',
              'key3' => 'val3'
            };
    

    我发现这个tutorial 很好地解释了环视。

    【讨论】:

      【解决方案2】:

      困难在于确定每个键的值列表的结束位置。最明显的是,它可以在字符串的末尾,或者更隐晦地,在另一个键|值对开始的地方。 (这是一个可怕的设计。能在你发现更难解决的问题之前解决它吗?)

      此解决方案的工作原理是为“键”字符串(除竖线、逗号或空格之外的任何内容)定义正则表达式,然后使用它为完整的键|值对构建模式,该对在结尾处结束字符串或另一个“逗号 - 键 - 管道”序列开始的地方。

      use strict;
      use warnings;
      
      my $s = 'key1|val1,key2|val2_a,val2_b,val2_c,key3|val3';
      
      my $key_re = qr/ [^|,\s]+ /x;
      
      my @pairs = $s =~ / $key_re \| [^|\s]+ (?= \z | , $key_re \| )/gx;
      
      print "$_\n" for @pairs;
      

      输出

      key1|val1
      key2|val2_a,val2_b,val2_c
      key3|val3
      

      【讨论】:

      • 感谢您的解释。效果很好。我希望我能改变设计,但我只是在消耗数据。
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2020-04-27
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-03-12
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多