Shell

雙引號和單引號內的Grep字元串

  • June 24, 2020

我想在文本文件中找到雙引號或單引號內的字元串(文本文件是多行的),

例如:

I have a 
test "foo bar1" test2 "foo\"bar2", 
"foo 'bar3", 
'foo bar4', 'foo \'bar5', 'foo "bar6',

它會輸出

foo bar1
foo\"bar2
foo 'bar3
foo bar4
foo \'bar5
foo "bar6

難點是:

  1. 文本文件是多行的。
  2. 它可能在引號內轉義了雙引號或單引號。
  3. 雙引號裡面可能有單引號。
  4. 單引號裡面可能有雙引號。
  5. 引號必須成對匹配。

我們可以使用 Perl 的匹配時間程式碼插值功能(??{ match time regex }) 來解決這個問題。本質上,它所做的是,根據匹配的引用,它將相應的有效正則表達式放置在該引用中,以便正則表達式引擎將獲取該引用對。

$ perl -lne '
   print substr($&, 1, -2+length($&))
     while
        /(?:(["'\''])(??{q<(?:[^\\\\>.$1.q<]|\\\\.)*>.$1}))/gx;
' file

結果:

foo bar1
foo\"bar2
foo 'bar3
foo bar4
foo \'bar5
foo "bar6

上面的更平滑的重寫如下:

$ perl -lne '
   BEGIN {
      $genRE = sub {
         my $openingQ = shift;
         # look in the Notes below for why
         qq<(?:[^\\\\${openingQ}]|\\\\.)*>
      };
   }
   print $2
     while 
       /
        (["'\''])               (?#: opening quote) 
         ((??{ $genRE->($1) })) (?#: run of in between quote pair stuff) 
        \1                      (?#: corresponding closing quote)
       /gx;
' file

筆記::

  • "........"被匹配/"[^"]*"/
  • "...... \"......"被匹配/"(?:[^\\"]|\\.)*"/
  • 單引號也類似。

引用自:https://unix.stackexchange.com/questions/594261