0

各行で非常に多くの一致があった後にのみ開始する単純な文字列を検索して置換したい、たとえば:

n=2 の場合は s/ZZ/YY

xxxZZxxxxxxZZxxxxZZxZZxxxxZZ
xZZxxxZZxxZZxxZZxZZxxxZZxxx
...

の中へ:

xxxZZxxxxxxZZxxxxxYYxxxxYY
xZZxxxZZxxYYxxYYxYYxxxYYxxx
...

私の問題では、連続する「ZZ」の間に常に「x」があります。前もって感謝します。

4

4 に答える 4

4

これまでに見られた一致の数を数えることができる実行可能な置換文字列をお勧めします

このコードは

use strict;
use warnings;

while (<DATA>) {
  my $n = 0;
  s/(ZZ)/$n++ < 2 ? $1 : 'YY'/eg;
  print;
}

__DATA__
xxxZZxxxxxxZZxxxxZZxZZxxxxZZ
xZZxxxZZxxZZxxZZxZZxxxZZxxx

出力

xxxZZxxxxxxZZxxxxYYxYYxxxxYY
xZZxxxZZxxYYxxYYxYYxxxYYxxx
于 2012-09-18T21:15:08.337 に答える
3

おそらく、後読みの解決策、または文字列を逆にして先読みし、もう一度逆にする解決策があります(もしあれば、私はそれらに賛成します)が、私は通常while、発見しやすく、間違いなく読みやすくなります。

1 while $string =~ s/(ZZ.*ZZ.*)ZZ/$1YY/

つまり、文字列には3つのパターンが含まれていますがZZ、3番目のパターンを。に置き換えYYます。

一般的な解決策として:

$expr = (quotemeta($pattern1) . ".*") x $n;
1 while $string =~ s/($expr)\Q$pattern2\E/$1$pattern2/;
于 2012-09-18T20:57:32.960 に答える
1
1 while $thisline=~s/((?:x*?ZZx*?){2}[xZY]*?)ZZ/$1YY/;

これは n=2 の場合の解です。

n の他の値については、そこで数値を変更するだけです。

また、遅延マッチングを使用して置換を最適化し、余分なキャプチャーを排除しました。

于 2012-09-19T13:46:17.557 に答える
1

最も単純な perl ソリューション次のように思われます:1 while s/ZZ/YY/3が、perl はそれを受け入れません。で同じことをしてsedください:

sed ':a
  s/ZZ/YY/3
  ta'

のいくつかの実装ではsed、これをより簡単sed ':a; s/ZZ/YY/3; ta'に書くことができます:sed -e :a -e s/ZZ/YY/3 -e ta

于 2012-09-18T21:25:49.067 に答える