由于我对 Linux 工具的了解有限,我遇到了困难。由于我的文件列表包含空格(空格字符),因此“find”命令无法找到任何命中,但不会产生任何错误。此脚本的原因是帮助对先前已转码的文件(例如音乐或电影)进行(重新)转码。
searchdir="/volume2/"
filename='list-in.txt'
n=1
while read line; do
echo "# $n : $line"
FILES=${line%.*}
find ${searchDir} -iname "$FILES.*" -type f
n=$((n+1))
done < $filename
我不知道从这里开始哪里,因为我发现 awk 或 sed 示例很少处理处理变量。
输入文件将包含以下形式的文件名:
Supertramp [The Very Best Of Supertramp] -05- Breakfast In America.m4a
Supertramp [The Very Best Of Supertramp] -07- Take The Long Way Home.m4a
Supertramp [The Very Best Of Supertramp] -09- Dreamer.m4a
没有引号分隔,也没有路径。
脚本的输出将是与上面列表最匹配的路径和文件名。请注意,源文件和结果具有不同的文件扩展名:
/volume2/music/Supertramp/1990. The Very Best Of Supertramp/Supertramp [The Very Best Of Supertramp] -05- Breakfast In America.flac
/volume2/music/Supertramp/1990. The Very Best Of Supertramp/Supertramp [The Very Best Of Supertramp] -07- Take The Long Way Home.flac
/volume2/music/Supertramp/1990. The Very Best Of Supertramp/Supertramp [The Very Best Of Supertramp] -09- Dreamer.flac
答案1
使用 zsh shell:
set -o extendedglob
searchdir=/volume2
filename=list-in.txt
names=( ${(f)"$(<$filename)"} )
files=( $searchdir/**/(#i)(${(~j[|])names:r}).*(ND.) )
print -rC1 -- $files
除了在(#i)
此处启用不区分大小写的匹配之外,您还可以启用近似匹配。例如,(#a2)
允许匹配最多有 2 个错误(遗漏、插入、转置、不同字符)。
$(<file)
扩展到 的内容file
。这里引用它是为了防止 IFS 吐槽。${(f)expansion}
在行上分割扩展f
。${file:r}
扩展为r
文件的 ootname(删除扩展名)。当应用于数组时,这适用于所有元素。${(j[|])array}
j
用 加入数组元素|
。对于~
,它|
被视为全局运算符(交替)。**/
匹配任何级别的子目录(包括 0 级)。(ND.)
: 全局限定符:N
ullglob:如果没有匹配则不会出错D
otglob:还查找隐藏文件.
仅匹配常规的文件(如-type f
的find
)。