0

単語が出現する<Annotation>との間のすべてのテキストを取得する必要があります。VIMでどうやってそれを行うことができますか?</Annotation>MATCH

<Annotation about="MATCH UNTIL </Annotation>   " timestamp="0x000463e92263dd4a" href="     5raS5maS90ZWh0YXZha29rb2VsbWEvbGFza2FyaS8QyrqPk5L9mAI">                                                                        
  <Label name="las" />
  <Label name="_cse_6sbbohxmd_c" />
  <AdditionalData attribute="original_url" value="MATCH UNTIL </Annotation>       " />
</Annotation>
<Annotation about="NO MATCH" href="     Cjl3aWtpLmhlbHNpbmtpLmZpL2Rpc3BsYXkvbWF0aHN0YXRLdXJzc2l0L0thaWtraStrdXJzc2l0LyoQh_HGoJH9mAI">
  <Label name="_cse_6sbbohxmd_c" />
  <Label name="courses" />
  <Label name="kurssit" />
  <AdditionalData attribute="original_url" value="NO MATCH" />
</Annotation>
<Annotation about="MATCH UNTIL </ANNOTATION>     " score="1" timestamp="0x000463e90f8eed5c" href="CiZtYXRoc3RhdC5oZWx     zaW5raS5maS90ZWh0YXZha29rb2VsbWEvKhDc2rv8kP2YAg">
  <Label name="_cse_6sbbohxmd_c" />
  <Label name="exercises_without_solutions" />
  <Label name="tehtäväkokoelma" />
  <AdditionalData attribute="original_url" value="MATCH UNTIL </ANNOTATION>" />
</Annotation>
4

2 に答える 2

4

まず、免責事項:正規表現を使用してXMLをスライスおよびダイスする試みは、脆弱です。実際のXMLパーサーの方がうまくいくでしょう。

パターン:

\(<Annotation\(\s*\w\+="[^"]\{-}"\s\{-}\)*>\)\@<=\(\(<\/Annotation\)\@!\_.\)\{-}"MATCH\_.\{-}\(<\/Annotation>\)\@=

分解してみましょう...

グループ1は<Annotation\(\s*\w\+="[^"]\{-}"\s\{-}\)*>です。これは、属性要素の開始タグと一致します。グループ1に埋め込まれているグループ2は属性と一致し、0回以上繰り返される場合があります。

グループ2は\s*\w\+="[^"]\{-}"\s\{-}です。これらの部品のほとんどは一般的に使用されます。最も珍しいのは\{-}、です。これは、貪欲でない繰り返しを意味*?します(Perl互換の正規表現で)。最後の貪欲でない空白の一致は、パフォーマンスにとって重要です。\s*それがなければ、Vimはグループ2の終わりとグループ2\s*の次の出現の始まりの間で属性間の空白を分割するためにあらゆる可能な方法を試みます。

グループ1の後には\@<=。これは、ゼロ幅のポジティブルックビハインドです。一致したテキストに開始タグが含まれるのを防ぎます(たとえば、s ///の場合)。

グループ3は\(<\/Annotation\)\@!\_.です。これには、属性の終了タグの先頭に一致するグループ4が含まれます。これ\@!はゼロ幅の負の先読みであり、\_.任意の文字(改行を含む)に一致します。一緒に、このグループは、属性終了タグが始まる場所を除いて、任意の文字で一致します。グループ3の後には、貪欲でない繰り返しマーカーが続き、\{-}MATCHの前のテキストの最小ブロックと一致します。グループ3の代わりに使用する場合\_.、一致したテキストには、MATCHを含まない注釈要素の終了タグが含まれ、MATCHを使用して次の注釈要素に進むことができます。(それを試してみてください。)

次のビットは簡単です。終了タグの前にあるMATCHと他の最小数の文字を見つけます。

グループ5は簡単です:それは終了タグです。\@=はゼロ幅の正の先読みです。これは\@<=、開始タグの場合と同じ理由でここに含まれています。幅がゼロの修飾子を持つグループはキャプチャされないため<\/Attribute、使用するのではなく繰り返す必要があります。\4

于 2009-04-10T02:42:13.610 に答える
3

vim内で行う必要がありますか?ごまかして、vim 内で移動する行番号を示す more/less に何かをパイプする 2 番目のウィンドウを開くことはできますか?

- 編集 -

vi[m] で複数行の一致/検索を行ったことはありません。ただし、別のウィンドウでカンニングするには:

perl -n -e 'if ( /<tag/ .. /<\/tag/)' -e '{ print "$.:$_"; }' file.xml | less

「タグ」(または他の長い一致する名前)の要素/ブロックを行番号とともに表示し、各ブロック内の他のテキストを検索できます。

十分近い?

- 編集 -

「少ない」内で、入力します

/MATCH

MATCH の出現を検索します。左マージンには、そのインスタンス (対象の要素/タグ内) がある行番号が表示されます。

vi[m] 内で、次のように入力します。

:n

ここで、「n」は目的の行番号です。

もちろん、本当にやりたかったことが何らかの検索/ヤンク/置換である場合は、さらに複雑になります。その時点で、awk / perl / ruby​​ (または好みに合った類似のもの...または xsl?) は、実際に変換に使用する必要があるツールです。

于 2009-04-10T01:13:33.683 に答える