指定された行番号でsed操作を実行します


8

行番号が事前に割り当てられている特定の行を操作する簡単な方法があるかどうか疑問に思っています。

ファイルの1、7、14、16行目を出力したいとしましょう。

sed -n '1p;7p;14p;16p' input_file

しかし、操作が印刷だけではなく、同じ長いコマンドを4回書きたくない場合、これはさらに複雑になります(そして、はい、同じbash変数を4回代入することで、この長いsedコマンドを作成できることを知っていますが、それは十分に理想的ではありません...)、すなわち

sed -n '1{long_command};7{long_command};14{long_command};16{long_command}' input_file

私のファイルのこれらの特定の行で操作を行う方法はありますか?私は次のようなものを期待しています、

sed -n '1,7,14,16p'

これは確かに現在の形式では機能しません。

どんな助けでもありがたいです。「いいえ、それは不可能です。」説明付きは私が受け入れる答えでもあります。


それは簡単ですawk
RomanPerekhrest

回答:


11

ブランチを使用できます:

sed '
  1b1
  7b1
  14b1
  16b1

  # for the rest to be left alone, branch off (or delete them with "d"):
  b

  :1
  long_command'

20,25b1行の範囲を追加したり/re/b1、に一致する行を含めることもできますre)。

またはあなたが使うことができますawk

awk 'NR == 1 || NR == 7 || ... {stuff}'

またはハッシュを使用:

awk -v l=1,7,14,16 '
  BEGIN{split(l, a, ","); for (i in a) lines[a[i]]}

  NR in lines {stuff}'

(またはBEGIN{lines[1]lines[7]lines[14]lines[16]}あまり多くない場合)


ありがとう、ブランチについて考えたことはありません...これは、この場合に使用する理想的なツールのようです。
Weijun Zhou

このようなブランチを検索パターンと一緒にsedで使用するにはどうすればよいですか?たとえば、n行目以降のパターンを一致または削除したいですか?
qodeninja

3

単に選択を反転して削除します。

sed '2,6d;8,13d;15d;17,$d;long_command'

これは、たとえばstdinから読み取られる行番号を処理するのが少し難しいが、優れたソリューションでもあります。
Weijun Zhou

1

最初のバリアント:

あなたはこのトリックを使うことができます:

sed -nf <(printf '%dp\n' 1 7 14 16)

-f スクリプトファイル - スクリプトファイルの内容を実行するコマンドに追加します。

テスト中

seq 1 20 | sed -nf <(printf '%dp\n' 1 7 14 16)

出力

1
7
14
16

2番目のバリアント:

最初sedは、ファイルから必要な行のみをフィルタリングするために補助が使用され、次にこれらの行sedがlongコマンドでメインにパイプされます。

sed -n '1p; 7p; 14p; 16p' input.txt | sed 'long command'
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.