Linux 用户!我遇到了一个问题:目录中有所有 pdf 文件Downloads
,但我想复制子文件夹中的所有文件\Download\BOOKS\
。我该如何for
循环复制所有文件?
for files in ...
答案1
不使用 for 循环,但这应该可以工作移动文件。
mv /home/username/Downloads/*.pdf /home/username/Downloads/BOOKS
使用它来制作复制文件:
cp /home/username/Downloads/*.pdf /home/username/Downloads/BOOKS
答案2
现有的答案都还不错,但都有一些小问题,可能有问题,也可能没问题。让我们试着解决它们。
- 所有文件都正确吗
*.pdf
?我发现从互联网上下载的 PDF 经常是*.PDF
这样的。(我怀疑某些不区分大小写的文件系统会导致这种情况。) - 例如,
BOOKS/Romance
所有PDF 是否都直接位于 BOOKS 子目录中,或者是否有子目录?BOOKS/Horror
- PDF 有文件扩展名吗?有时没有。
- 是否有任何文件是符号链接的?不太可能,但处理起来并不难。
- 已经指出但值得重复:任何文件名是否包含空格或其他奇怪字符?空格对于人类可读性来说是相当常见的。
该策略用于find
定位潜在的 PDF、file
仅过滤实际的 PDF,然后对这些文件名采取行动。
find -L books -maxdepth 1 -print0 | xargs -0 -n1 -I{} sh -c '[ "$(file -b --mime-type "{}")" = "application/pdf" ] && cp "{}" Download/'
find -L Download/BOOKS -maxdepth 1 -print0
将从 开始查找子目录树中的所有文件系统条目Download/BOOKS
,如果需要则跟踪符号链接,直至最大深度。增加深度数字以处理子目录,或删除-maxdepth 1
以处理整个树。
xargs -0 -n1 -I{}
接受多行输入并使用 1 行输入重复运行命令。
sh -c '[ "$(file -b --mime-type "{}")" = "application/pdf" ] && cp "{}" Download/'
创建一个新的 shell 来对文件系统条目运行测试,如果它是 PDF(由文件扩展名和文件内容确定)则将其复制到目录中Download/
。
使用find
可处理 1.、2. 和 4。使用file
可处理 3。使用-print0
和-0
参数并仔细引用可处理 5。
如果您确实需要循环,因为您想在每个 PDF 上运行其他命令,请cp "{}" Download/
用适当的内容替换。这{}
是 xargs 在运行时将用每个文件名替换的模式。
答案3
我认为您不需要for
循环来复制文件。您可以使用以下方法复制文件:
cp /home/username/Downloads/*.pdf /home/username/Downloads/BOOKS
但如果你仍然想使用for
循环,你也可以编写下面的代码:
cd /home/username/Downloads
for F in *.pdf
do
cp "$F" /home/username/Downloads/BOOKS
done
答案4
一个简单的 for 循环应该能够完成您需要的操作,即将下载(包括子目录)下的所有 PDF 文件复制到下载/图书中
cd Downloads
IFS=$(echo -en "\n\b") && for n in `find . -path ./BOOKS -prune -o -name "*.pdf" -print`; do cp -fv "$n" ./BOOKS; done
注意,find语句的单引号是向后单引号,而不是普通单引号。
已编辑:文件名中的空格需要内部字段分隔符。