![仅将常规文件从一个目录复制到另一个目录](https://linux22.com/image/4361/%E4%BB%85%E5%B0%86%E5%B8%B8%E8%A7%84%E6%96%87%E4%BB%B6%E4%BB%8E%E4%B8%80%E4%B8%AA%E7%9B%AE%E5%BD%95%E5%A4%8D%E5%88%B6%E5%88%B0%E5%8F%A6%E4%B8%80%E4%B8%AA%E7%9B%AE%E5%BD%95.png)
我想将目录 1 的内容复制到目录 2。但是,我只想从目录 1 复制文件(而不是目录)。我该怎么做?
cp dir1/* dir2/*
那么我仍然有目录问题。
另外,我的所有文件都没有任何扩展名,所以*.*
不会成功。
答案1
cp dir1/* dir2
cp
不会复制目录,除非明确告知这样做(例如--recursive
,请参阅man cp
)。
注1: cp
很可能会以非零状态退出,但文件无论如何都会被复制。当基于退出代码链接命令时,这可能是一个问题:&&
、||
、if cp -r dir1/* dir2; then ...
等(感谢康特比斯为了他们对此问题的评论)
笔记2:cp
期望最后一个参数是单个文件名或目录。*
目标目录名称后面确实不应该有通配符。dir2\*
将被 shell 扩展,就像dir1\*
.意想不到的事情将要发生:
- 如果
dir2
为空并且取决于您的 shell 和设置:- 您可能只会收到一条错误消息,这是最好的情况。
dir2/*
将按字面意思理解(查找名为 的文件/目录*
),这也可能会导致错误,除非*
实际存在。dir2/*
它将完全从命令中删除,留下cp dir1/*
.根据 的扩展dir1/*
,这甚至可能会破坏数据:- 如果
dir1/*
仅匹配一个文件或目录,您将收到错误cp
。 - 如果
dir1/*
恰好匹配两个文件,则一个文件将被另一个文件覆盖(坏的)。 - 如果
dir/*
匹配多个文件并且最后一个匹配是 a,您将收到一条错误消息。 - 如果最后一个匹配项
dir/*
是一个目录,则所有其他匹配项都将移至该目录中。
- 如果
- 如果
dir2
不为空,则再次取决于:- 如果 的最后一个匹配
dir2/*
是一个目录,dir1/*
则 的其他匹配dir2/*
将被移入。 - 如果最后一个匹配
dir2/*
是一个文件,您可能会收到一条错误消息,除非dir1/*
只匹配一个文件。
- 如果 的最后一个匹配
答案2
扩展通配符的是 shell,而不是命令。因此,cp dir1/* dir2/*
首先扩展两个通配符,然后调用cp
结果。这根本不是您所期望的:根据 中已有的文件数量dir2
,dir2/*
可能会扩展为一个或多个参数。该命令cp
不知道哪些参数来自扩展第一个模式,哪些参数来自扩展第二个模式。它期望最后一个参数是目标目录的名称。因此,要将所有文件从目录复制dir1
到目录中dir2
,最后一个参数必须是目录dir2
:
cp dir1/* dir2
由于*
匹配所有文件,cp
因此尝试复制所有文件。这包括目录:目录也是文件。它跳过目录,但报告错误。它复制特殊文件的内容,例如命名管道(最好有东西写入它们,否则cp
会阻塞)等。
仅复制常规的文件,您需要限制匹配。在 zsh 中,您可以使用全局限定符 .
为了那个原因:
cp dir1/*(.) dir2
其他外壳没有这个。您可以使用该find
命令来过滤文件类型。假设您运行的是非嵌入式 Linux 或 Cygwin:
find dir1 -maxdepth 1 -type f -exec cp -t dir2 {} +
在 Linux、FreeBSD 和 OSX 上:
find dir1 -maxdepth 1 -type f | xargs -I {} cp {} dir2
答案3
您可以使用“rsync”代替“cp”
rsync -vt dir1/* dir2/
它更干净,在某些情况下更快
答案4
以下是将文件从源目录复制到目标目录的命令。
转到源文件夹然后编写以下命令:
$ cp fileName destination directory path
例子:
cp publichOT.sh /data/home/useradmin