我可以使用find -exec命令查找并将所有文件复制到给定文件夹。 但我需要做的是找到并复制给定路径中的所有文件及其保存文件夹。所以......
/path/to/file/is/abc.txt
/another/file/is/here/xyz.txt
我需要将这两个文件及其路径复制到以下文件夹:
/ MySQL的/数据/
新文件结构将如下所示......
/mysql/data/is/abc.txt
/mysql/data/here/xyz.txt
这样做是为了避免可能覆盖重复的文件名。最后的文件夹名称将是唯一的,但文件名可能相同。
这样做的最佳方式是什么?
答案 0 :(得分:3)
这是一个简洁的脚本,附带相当长的解释 * 。
for oldpath in $your_file_list; do
mv ${oldpath} /mysql/data${oldpath##$(dirname $(dirname $oldpath))}
done
工作原理
dirname
实用程序会删除路径中包含最后一个正斜杠(/
)的所有内容。调用它两次将删除所有内容,包括倒数第二个斜杠。
习语$(command with params)
使用参数command
执行with params
并返回输出。
成语${var##prefix}
会删除已移除var
的变量prefix
的内容。
分步分析
如果oldpath
为/path/to/file/is/abc.txt
,则为:
dirname $oldpath
是/path/to/file/is
dirname $(dirname $oldpath)
是/path/to/file
${oldpath##$(dirname $(dirname $oldpath))}
是/is/abc.txt
是原始路径中将附加到新路径的部分。
* 优雅( adj。)软件:任何实现算法的软件,其解释更长而不是实施本身。
答案 1 :(得分:1)
您将不得不编写此程序的脚本/编程。
快速python示例如下:
import os
import shutils
src_root = '/path/to/walk/'
dst_root = '/mysql/data/'
for root,dirs,files in os.walk(src_root):
for file in files:
dst_path = os.path.split(root)[1]
dst_path = os.path.join(dst_root, dst_path)
os.makedirs(dst_path)
src = os.path.join(root,i file)
dst = os.path.join(dst_path, file)
shutils.copyfile(srd, dst)
答案 2 :(得分:1)
这可能对您有用:
a=/mysql/data
sed 's|.*\(/[^/]*/[^/]*\)|mv -v & '"$a"'\1|' file
mv -v /path/to/file/is/abc.txt /mysql/data/is/abc.txt
mv -v /another/file/is/here/xyz.txt /mysql/data/here/xyz.txt
研究输出,如果一切正常,则运行:
sed 's|.*\(/[^/]*/[^/]*\)|mv -v & '"$a"'\1|' file | bash
答案 3 :(得分:0)
如果要先复制文件,则需要为其创建目录。您可以使用单个查找命令来执行此操作,但我不确定此解决方案的效率?
#!/bin/bash
# $1 - destination
find $1 -type f -exec bash -c '
dest="$2"; # $2 is second argument passed to the script
dir=$(basename $(dirname $1));
mkdir $dest/$dir 2>/dev/null;
cp $1 "$dest/$dir/";
' -- {} $2 \; # {} = $1 in bash '..' and $2=$2
用法:./ copy copy_from copy_to
编辑: 看起来更好:
#!/bin/bash
dest=$2
from=$1
# copy_file from dest
copy_file() {
dir=$(basename $(dirname $from))
mkdir $dest/$dir
cp $from $dest/$dir
}
find $from -type f | while read file; do copy_file $file $dest; done