正規表現を使用したVimの置換について

こんにちは、Habr! 古いVimがさまざまな問題の解決に非常に優れていることは周知の事実です。 私たちのお気に入りのエディターを強力にするのと同じくらい強力にするコンポーネントの1つ、つまり正規表現を使用する置換用のツールキットについて少しお話ししたいと思います。 いくつかの特定の問題をどのように解決したかを説明し、基本的な背景情報でこのストーリーを補足することで、ストーリーを構築する予定です。





一方では、このすべてについて、アドレスで詳細なヘルプを利用できます:help usr_27.txt-そこからすべてが収集されました。 一方、説明した問題を解決する必要があるとき、私はこれにかなりの時間を費やしました。 これにより、私のテキストが引き続き有用であることを希望する権利が与えられます。 私はプログラミングからは程遠い人であるという予約をしたいので、私の用語は奇妙またはばかげているように見えるかもしれません-これを許してください。



htmlファイルからすべてのタグを削除する必要に直面したとき。 少し考えた後、三角形の括弧で囲まれたすべてのものを空のスペースに置き換えるだけでよいと判断しました。 こちらが代替品です



<''> -> ' ' ().







Vimでの検索と置換は、コマンド:substitutionによって実行されますが、略語sを使用する方がはるかに便利です。 このコマンドの一般的な構文は次のようなものです。



:{}s/{ }/{ }/{}







要素{limits}には、置換を実行する領域を含める必要があります。 この要素を省略すると、カーソルのある行でのみ検索と置換が実行されます。 「%」文字を使用して、ファイル全体を置き換えることができます。 行l1で始まり行l2で終わる領域で検索および置換するには、{limits}の形式は 'l1、l2'でなければなりません。たとえば、14.17 s /は行14〜17で検索および置換されます。 カーソルのある行(その数はドットで象徴的に示され、最後の行(その数はドル記号で示されます))は特筆に値します。 したがって、現在の行からファイルの末尾までを検索するには、コマンド「:。、$ S /」を使用します。



このコマンドはすべて、指定された制限内で、「置換対象」要素の基準を満たすシーケンスを検索し、最後のスラッシュの後に指定されたオプションを考慮して、「置換対象」要素のルールに従って構築された文字シーケンスでこのシーケンスを置き換えます。



私が問題を解決しようとした最初のチームは次のとおりでした



:%s/<.*>//g







最初のスラッシュまで、ファイル全体に検索および置換コマンドがあります。 最初と2番目のスラッシュの間に、Vimが探すシーケンスがあります。 彼女についての詳細。



最初に三角形の括弧があり、Vimは文字通りの一致を探します。 ドットは任意の文字を示し、アスタリスクは、ゼロから無限までの任意の回数の前の文字の出現を示します。 したがって、シーケンス '。*'は、任意の文字のシーケンスを示します。 最後に、三角ブラケットをさらに閉じます。 はい、「三角括弧」という用語が、これらが「より少ない」兆候であることを覚えている人の認識を損なう場合は謝罪します(:



2番目と3番目のスラッシュの間には、指定された基準を満たすシーケンスの代わりに置換される一連の文字があります。 大量の削除が必要なので、何もありません。



コマンドを完了する文字gは、ストリング全体の検索を示します。 それ以外の場合、Vimは{limits}内の各行で最初に一致したもののみを検索します。 別の便利なオプションは、検索のみを実行し、置換しないオプション(n)です(有効な検索条件が目的の検索条件と一致するかどうかを確認するのに役立ちます)。また、置換操作ごとに確認を求める「c」です。



したがって、説明されているコマンドは、三角括弧で囲まれた文字で構成されるシーケンスを検索します。 Vimはそのようなシーケンスをすべて削除します。 残念ながら、三角形の括弧の間で文字を検索するため、このコマンドは適切に動作しません。 他の三角括弧を含む。 そのため、1行に複数の三角カッコのペアがある場合、Vimは最初の開始から始まり、最後の三角カッコで終了するシーケンスを選択します。



結論はそれ自身を示唆しています。三角形の括弧の間の文字を探す必要があります。ただし、閉じている三角形の括弧を除きます。 この場合、Vimには対応するコマンドがあります。 必要なシーケンスを記述するときに、特定の文字セットを角かっこで囲むと、Vimはこれらの角かっこから何かを探します。 たとえば、パターン「[az]」は小文字のラテン文字を満たします。 角かっこで囲まれた最初の文字が '^'帽子の場合、角かっこ内にあるもの以外が見つかった場合、Vimは満足します。 私たちの場合、フレーズ



[^>]







閉じている三角括弧以外のものに一致します。 ここで、Vimが角括弧のペアに対して1文字のみを検索することを追加する必要があります。 つまり 最後に書き込まれたパターンは、閉じ三角括弧を除いて、任意の1文字で満たされます。 このシーケンスが必要な数の文字を満たせるようにするには、アスタリスクを追加する必要があります。 その結果、必要なチームは次の形式を取ります



:%s/<[^>]*>//g







このようなタスクが、たとえばメモ帳やVimでどのように解決されるかを把握できます。 メモ帳では、最初に最も人気のあるタグを空のスペースに大量に置き換えます(たとえば、最初に 'p'タグを空のスペースに置き換え始めます)。次に、三角形の角かっこを探し、それらとその中身を削除します。 非常に大きなファイルを処理するのに時間がかかります。 そして、ここではすべてが1つのチームで成り立っています-それはとても簡単です。



もう1つのタスクについて-義務の問題として、出力に多くのASCII情報を提供するWolfram Mathematicaプログラムを使用する必要があります。このプログラムは、読みやすくするために処理する必要があります。 たとえば、ある式の絶対値を見つけると、このプログラムは単語「Abs」を示し、この式を角括弧で囲みます。 私は、ラテックスを通過した数学テキストを読むのが好きで、絶対値を見つけることは垂直スティック(垂直バー)で指定するのに完全に自然です。 そのため、ファイル全体を置換する必要があります



Abs[ '' ] -> | '' |







「Abs」という単語のすべての出現を削除する必要がある場合、それは非常に単純で前のタスクに似ていますが、この場合は「式」も保存する必要があり、そのたびに新しいものになります。 どうする? グループ化チームが助けになります。 目的のシーケンスを記述するときに、式を角かっこ\(\)で囲むと、Vimはそれを対応する番号の下のメモリに配置し(最初の式は番号1の下にあり、2番目は2になります)、その後コマンドxで呼び出されます(xは番号)その下に式がメモリに配置されました。



したがって、目的のコマンドは次のようになります。



:%s/Abs\[\([^\]]*\)\]/|\1|/g







ここで、リテラルマッチの場合、角括弧は特殊文字であるため、スラッシュが前に付いていることに注意してください。 一般に、検索に参加する必要がある特殊文字は、その即時の意味を示し、スラッシュが前に付きます:\ ^; \ *など スラッシュ自体の前にもスラッシュが付いています。 次のようになります。シーケンス「\ cos」を検索するには、「\\ cos」と入力します。



最後に、私が書きたい最後のタスク。 同じMathematicaは多くの数量で動作し、それらは1桁の数字インデックスを持つ大文字のラテン文字で示されます。 ASCII形式では、これらのラテン文字と数字は、たとえば 'U1'のように単純に連続します。 ラテックスがそれらをインデックス付きの文字として扱うためには、インデックスの前にアンダースコア文字「_」が必要です。 タスクの概要-ビューを変更する



' ''' -> ' '_''







それ自体を示唆する最も些細な解決策は、多くない場合、すべての組み合わせをソートすることです。 つまり、最初に「U1」->「U_1」、次に「U2」->「U_2」などの交換を開始します。 これが私たちの方法ではないことは明らかです。 角括弧があることを思い出してください。 また、ラテン語で大文字を1つ見つけるには、テンプレート「[AZ]」を入力します。 しかし、これは制限ではありません。 そのようなテンプレートに対して、Vimには特別な略語があります: '\ u'( 'uppercase'から)。 数字の場合、「\ d」(「数字」から)があります。 このような設計の詳細については、help pattern.txtをご覧ください。 これらの略語を使用すると、検索コマンドは次の形式になります



:%s/\(\u\)\(\d\)/\1_\2/g







ここでもグループ化は括弧で囲まれています:検索時に対応する番号の下にあるメモリに見つかった文字と数字を入れ、その後そこからそれらを抽出し、同じ数字でコマンドを呼び出します:「\ 1」は文字を呼び出し、「\ 2」-数字を呼び出します。



これら3つの単純なタスクは、検索と置換におけるVimの機能を完全に実証しているように思えます。 メモ帳やメモ帳++などのテキストエディタを手に持ってそれらの1つを解決する必要がある場合、私が解決に費やす時間は私が乗るのに費やす時間を大幅に超えると信じていますVimのコピーを持つ同じマシン(:



All Articles