ファイル名から5番目_前の部分を抽出したいですか?

ファイル名から5番目_前の部分を抽出したいですか?

ファイルがありますabc_asdfjhdsf_ckd_dfksfj_c_12345678_223344.txt。出力になりたいですabc_asdfjhdsf_ckd_dfksfj_c.txt

答え1

sedを使う

$ echo abc_* | sed -E 's/(([^_]*_){5}).*/\1/; s/_$/.txt/'
abc_asdfjhdsf_ckd_dfksfj_c.txt

仕組み:

  • s/(([^_]*_){5}).*/\1/

    これにより、グループ1(最大5番目)のファイル名の先頭がキャプチャされ、残りは_削除されます。

    もっと詳しく見ると、sedの代替コマンドは次の形式を持っています。正規表現はs/old/new/どこにありますか?oldこの例では、正規表現は([^_]*_){5}最初の5つの部分と一致します。この正規表現を括弧内に入れて、最初の5つの部分をグループ1に保存します。 (([^_]*_){5})これを。最初の5つのグループ以降のすべての項目と一致します。私達はこれらすべてを最初の5つのグループである 。\1.*\1

  • s/_$/.txt/

    それから最後の残りを_見つけて.txt

awkを使う

$ echo abc_* | awk -F_ '{print $1,$2,$3,$4,$5 ".txt"}' OFS=_
abc_asdfjhdsf_ckd_dfksfj_c.txt

_これは入力フィールドと出力フィールドの区切り文字として使用されます。したがって、最初の5つのフィールドを印刷し、その後に.txt

回避策:最後の2つの部分を削除してください。

上記のコードは最初の5つの部分を保持し、残りの部分を削除します。質問の例には7つのセクションがあり、どちらもピリオドを含みません。 いつもそうだったらもう1つのアプローチ(ヒント:Costas)は、最後の2つの部分を削除することです。

$ echo abc_* | sed -E 's/(_[^_]*){2}\././'
abc_asdfjhdsf_ckd_dfksfj_c.txt

答え2

ファイルの終わりの名前を変更する元の質問を参照すると、次のようになります。

ls abc*
abc_asdfjhdsf_ckd_dfksfj_c_12345678_223344.csv

ls abc* | cut -d_ -f1-5 | awk '{print $1".txt";}'
abc_asdfjhdsf_ckd_dfksfj_c.txt

答え3

for   f in ./*_*_*_*_*_?*.txt
do    [ -e "$f" ] &&
      printf %s.txt\\n "${f%"${f#*_*_*_*_*_?}"}"
done

答え4

使用bash パラメータ拡張:

for f in abc_*; do f="${f%_*}"; echo "${f%_*}.txt"; done

出力:

abc_asdfjhdsf_ckd_dfksfj_c.txt

${f%_*}f_最後の(含まれている)変数以降のすべての項目を削除した後に変数値を含むパラメータ拡張モード。

関連情報