假设我有以下源目录
source/
subdir1/file1
subdir1/file2
subdir2/file3
subdir3/file4
和目标目录
target
subdir1/file5
subdir2/file6
subdir4/file7
我想将源子目录的内容移动到右目标子目录,因此结果如下所示
target
subdir1/file1
subdir1/file2
subdir1/file5
subdir2/file6
subdir2/file3
subdir3/file4
subdir4/file7
是否有一些Linux命令要执行此操作,还是我必须自己编写脚本?
答案 0 :(得分:1)
为了suimmarize,重要的是移动,而不是复制。这排除了cp
和rsync
,但允许mv
。但是,mv
存在一个问题,即它不擅长将旧目录合并到新目录中。
在您提供的示例中,目标目录具有完整的目录树但缺少文件。如果是这种情况,请尝试:
cd /source ; find . -type f -exec sh -c 'mv "$1" "/target/$1"' _ {} \;
上面首先选择源作为cd /source
的当前目录。接下来,我们使用find
这是用于查找文件/目录的常用* nix实用程序。在这种情况下,请find
-type f
选项告诉它只查看文件。使用-exec
选项,我们告诉它将找到的任何此类文件移动到目标目录。
您可以选择如何处理两个目录树之间的冲突。你可以给mv
-f
选项,它会覆盖目标中的文件而不会询问,或者你可以给它-n
选项,它永远不会覆盖目标文件,或者你的罐头给它-i
选项,每次都会问你。
如果目标目录树缺少源中的某些目录,我们必须动态创建它们。这只会增加一些轻微的并发症:
cd /source ; find . -type f -exec sh -c 'mkdir -p "/target/${1%/*}"; mv "$1" "/target/$1"' _ {} \;
在我们尝试将文件移动到那里之前,mkdir -p
命令确保我们想要的目录存在。
表单${1%/*}
是一个名为"参数扩展"的shell强大功能之一的示例。此特定功能是后缀删除。通常,它看起来像${parameter%word}
,它告诉bash展开word
并将其从parameter
的末尾删除。在我们的例子中,参数的名称是1
,这意味着脚本的第一个参数。我们想删除文件名,只留下文件所在的目录。因此,单词/*
告诉shell删除最后一个斜杠和后面的任何字符。
上述命令同时使用单引号和双引号。必须完全复制它们才能使命令正常工作。
答案 1 :(得分:0)
要同步dorectory可能使用rsync
示例:
rsync -avzh source/ target/
更多信息man rsync
移动(无副本)
rsync --remove-source-files -avzh source/ target/