如何在'.'之前提取文件名的一部分 或延期前

sha*_*hah 14 string shell-script filenames

我有以下格式的文件:

abc_asdfjhdsf_dfksfj_12345678.csv
hjjhk_hkjh_asd_asd_sd_98765498.csv
hgh_nn_25342134.exe
Run Code Online (Sandbox Code Playgroud)

我想获得.最后一个之前和之后的值_

结果将如下所示:

abc_asdfjhdsf_dfksfj_12345678.csv   ----> 12345678
hjjhk_hkjh_asd_asd_sd_98765498.csv  ----> 98765498
hgh_nn_25342134.exe                 ----> 25342134
Run Code Online (Sandbox Code Playgroud)

小智 18

你也可以使用 awk,

$ echo "abc_asdfjhdsf_dfksfj_12345678.csv" | awk -F'[_.]' '{print $4}'
12345678
Run Code Online (Sandbox Code Playgroud)

它将字段分隔符设置为_or .。然后打印列号 4 将为您提供所需的结果(您也可能更喜欢$(NF-1)(但最后一个字段)而不是$4)。


Sté*_*las 13

如果您在 POSIX shell 变量中有文件名:

file=abc_asdfjhdsf_dfksfj_12345678.csv
n=${file%.*}   # n becomes abc_asdfjhdsf_dfksfj_12345678
n=${file##*_}  # n becomes 12345678.csv
Run Code Online (Sandbox Code Playgroud)

通过解释:

  • ${variable%pattern}就像$variable,从后端减去最短的匹配模式;
  • ${variable##pattern}就像$variable,减去来自前端最长匹配模式。

有关参数扩展的更多信息,请参阅这样的参考

如果文件名列表位于每行一个文件名的文本流中:

sed -n 's/.*_\(.*\)\..*/\1/p'
Run Code Online (Sandbox Code Playgroud)


cuo*_*glm 3

您可以使用 GNU grep

$ echo abc_asdfjhdsf_dfksfj_12345678.csv | grep -oP '(?<=_)\d+(?=\.)'
12345678
Run Code Online (Sandbox Code Playgroud)

解释

  • (?<=)是lookbehind,(?<=_)匹配模式之前的下划线_
  • \d+匹配一个或多个数字。
  • (?=)是向前看,(?=\.)匹配模式后的点.

整个正则表达式意味着匹配_和之间的所有内容.