sed は、特定の文字を含む正確な行数を削除します。

sed は、特定の文字を含む正確な行数を削除します。

含まれている行を削除したいです。窒素キャラクターのインスタンスです。この場合、文字は/

私はプログラムを使用することを好みますsed

答え1

使用する必要がある場合、sedコマンドは次のとおりです。

sed -E -- '\-^([^/]*/[^/]*){3}$-d'

しかし、使用する必要がない場合は、sed最も簡単な解決策はを使用することですgrep

このコマンドのNを希望の値に置き換えます。窒素:

egrep -vx '([^/]*/[^/]*){N}'

grepこれを行うすべての行を表示-vするコマンドラインオプションがあります。grepいいえ正規表現を一致させます。したがって、次のタスクは、N個のスラッシュ文字を含む行に一致する正規表現を正確に作成し、その正規grep -v表現を使用することです。

例は次のパターンです。

[^/]*/[^/]*

N インスタンスはパターンです。

([^/]*/[^/]*){N}

正確にN個のインスタンスのパターンは次のとおりです。

^([^/]*/[^/]*){N}$

行全体にのみ一致するパターンのコマンドラインオプションgrepもあります(例:この例)。-x

だからNを3としましょう。正規表現は、3つのインスタンスを持つ行のみが確実に一致しますか/

$ cat << EOF | egrep -x '([^/]*/[^/]*){3}'
/
//
///
////
/stuff
/stuff/added
/stuff/added/
/stuff/added/to/
/stuff/added/to/each
/stuff/added/to/each/line
more/stuff
more/stuff/added
more/stuff/added/
more/stuff/added/to/
more/stuff/added/to/each
more/stuff/added/to/each/line
consecutive//slashes/
/consecutive//slashes/
/consecutive//slashes
///all in one place
all in one place///
all in ///one place
EOF
///
/stuff/added/
more/stuff/added/
consecutive//slashes/
/consecutive//slashes
///all in one place
all in one place///
all in ///one place

はい、正規表現が正しい行に一致しました。これで-vフラグを追加するだけです。ろ過行を一致させ、一致しない行を表示します。

$ cat << EOF | egrep -vx '([^/]*/[^/]*){3}'
/
//
///
////
/stuff
/stuff/added
/stuff/added/
/stuff/added/to/
/stuff/added/to/each
/stuff/added/to/each/line
more/stuff
more/stuff/added
more/stuff/added/
more/stuff/added/to/
more/stuff/added/to/each
more/stuff/added/to/each/line
consecutive//slashes/
/consecutive//slashes/
/consecutive//slashes
///all in one place
all in one place///
all in ///one place
EOF
/
//
////
/stuff
/stuff/added
/stuff/added/to/
/stuff/added/to/each
/stuff/added/to/each/line
more/stuff
more/stuff/added
more/stuff/added/to/
more/stuff/added/to/each
more/stuff/added/to/each/line
/consecutive//slashes/

答え2

/awk:を使用してフィールド区切り文字として指定し、フィールドn+1を見つけることもできます。

awk -F'/' -v n=3 'NF != n + 1' file

答え3

このpbmを使用できます。次のように:

$ perl -ne 'tr|/|/| == 3 || print' inp

ここでは、Perl関数のプロパティを使用して、tr入力文字列(この場合は現在のレコード)に対して実行された翻訳の数を返します。したがって、入力レコードに正確に3つのスラッシュがある場合、そのレコードは印刷されませんが、他のすべての場合は印刷されます。

今回使用された別の方法は次POSIX sedのとおりです。

$ sed -e 's:/:/:4;t' -e 's//\n/3' -e '/\n/d' inp

ここでは、まずスラッシュが3つ以上あるかどうかをテストし、その場合はパターンスペースを使用してsedコードの末尾に分岐します。 OTW、3つ以下のスラッシュがパターンスペースに表示されます。これで、\nパターンスペースで3番目のスラッシュを改行文字に置き換えることができるかどうかをテストします。この置き換え後に改行文字が表示された場合は、=>入力に正確に3つのスラッシュがあります。正確に3つのスラッシュを見たくないので、このパターン空間を削除します。 OTW、残りのもの(=>スラッシュが2つ以下のパターンスペース)は標準出力にインポートされます。

注:最後のケースでは置換が失敗した\nため見つかりません。s//\n/3

それを使用する別の方法はPOSIX sed次のとおりです。

$ sed -e h -e 's|[^/]||g' -e '/^.\{3\}$/d' -e g inp

スラッシュ以外のすべての文字が削除された現在のレコードのコピーを保存します。次に、パターンスペースに正確に3つの文字があることを確認します(実際にはすべてスラッシュです)。もしそうなら、すぐに削除します。 OTW、保留中に保存されたレコードを呼び出し、sedはデフォルトでそれを印刷します。

HTH。

答え4

1つのアプローチは次のとおりです。

  • 交換してみてください(代替)(N+1)キャラクターが初めて表示されます。交換が成功すると、新しいサイクルが始まります(四半期)。

  • 交換してみてください(代替)窒素文字が初めて表示されます。交換が失敗すると、新しいループが始まります(分岐)。

(その他)

  • この行を削除

GNU sedを使用してN = 2:

$ printf 'foo/\nfoo/bar/\nfoo/bar/baz/\n' | sed -e 's,/,/,3;t' -e 's,/,/,2;T' -ed
foo/
foo/bar/baz/

関連情報