Python – 移动并覆盖文件和文件夹

我有一个目录,“Dst目录”,其中有文件和文件夹,我有'src目录',其中也有文件和文件夹。 我想要做的是将'src目录'的内容移动到'Dst目录',并覆盖任何存在同名的文件。 因此,例如'Src Directory \ file.txt'需要移动到'Dst Directory'并覆盖现有的file.txt。 这同样适用于某些文件夹,移动一个文件夹并将内容与“dst目录”中的同一文件夹合并

我目前正在使用shutil.move将src的内容移到dst,但是如果这些文件已经存在并且不会合并文件夹, 它只会把文件夹放在现有的文件夹中。

更新:使事情更清楚一点; 我正在做的是将档案解压缩到Dst目录,然后将Src目录的内容移到那里并重新压缩,有效地更新zip档案中的文件。 这将重复添加新的文件或新版本的文件等,这就是为什么它需要覆盖和合并

解决:我解决了我的问题,通过使用distutils.dir_util.copy_tree(src,dst),这将从src目录中的文件夹和文件复制到dst目录,并覆盖/合并在哪里neccesary。 希望能帮助一些人!

希望有道理,谢谢!

使用copy()代替,它愿意覆盖目标文件。 如果你想要第一棵树消失,只要rmtree()它分开,一旦你完成了迭代。

http://docs.python.org/library/shutil.html#shutil.copy

http://docs.python.org/library/shutil.html#shutil.rmtree

更新:

在源代码树上执行os.walk() 。 对于每个目录,检查它是否存在于目标端,如果缺失则检查os.makedirs() 。 对于每个文件,只需shutil.copy()和该文件将被创build或覆盖,无论哪个适当。

这将通过源目录,创build目标目录中不存在的任何目录,并将文件从源移动到目标目录:

 import os import shutil root_src_dir = 'Src Directory\\' root_dst_dir = 'Dst Directory\\' for src_dir, dirs, files in os.walk(root_src_dir): dst_dir = src_dir.replace(root_src_dir, root_dst_dir, 1) if not os.path.exists(dst_dir): os.makedirs(dst_dir) for file_ in files: src_file = os.path.join(src_dir, file_) dst_file = os.path.join(dst_dir, file_) if os.path.exists(dst_file): os.remove(dst_file) shutil.move(src_file, dst_dir) 

任何预先存在的文件在被相应的源文件replace之前将首先被移除(通过os.remove )。 已经存在于目的地但不在源中的任何文件或目录将保持不变。

由于以上都没有为我工作,所以我写了我自己的recursion函数。 调用函数copyTree(dir1,dir2)来合并目录。 在多平台Linux和Windows上运行。

 def forceMergeFlatDir(srcDir, dstDir): if not os.path.exists(dstDir): os.makedirs(dstDir) for item in os.listdir(srcDir): srcFile = os.path.join(srcDir, item) dstFile = os.path.join(dstDir, item) forceCopyFile(srcFile, dstFile) def forceCopyFile (sfile, dfile): if os.path.isfile(sfile): shutil.copy2(sfile, dfile) def isAFlatDir(sDir): for item in os.listdir(sDir): sItem = os.path.join(sDir, item) if os.path.isdir(sItem): return False return True def copyTree(src, dst): for item in os.listdir(src): s = os.path.join(src, item) d = os.path.join(dst, item) if os.path.isfile(s): if not os.path.exists(dst): os.makedirs(dst) forceCopyFile(s,d) if os.path.isdir(s): isRecursive = not isAFlatDir(s) if isRecursive: copyTree(s, d) else: forceMergeFlatDir(s, d) 

如果您还需要使用只读标志覆盖文件,请使用以下命令:

 def copyDirTree(root_src_dir,root_dst_dir): """ Copy directory tree. Overwrites also read only files. :param root_src_dir: source directory :param root_dst_dir: destination directory """ for src_dir, dirs, files in os.walk(root_src_dir): dst_dir = src_dir.replace(root_src_dir, root_dst_dir, 1) if not os.path.exists(dst_dir): os.makedirs(dst_dir) for file_ in files: src_file = os.path.join(src_dir, file_) dst_file = os.path.join(dst_dir, file_) if os.path.exists(dst_file): try: os.remove(dst_file) except PermissionError as exc: os.chmod(dst_file, stat.S_IWUSR) os.remove(dst_file) shutil.copy(src_file, dst_dir) 

看看: os.remove删除现有的文件。

我有一个类似的问题。 我想移动文件和文件夹结构并覆盖现有文件,但不删除目标文件夹结构中的任何内容。

我解决了这个问题,使用os.walk() ,recursion调用我的函数,并使用shutil.move()我想覆盖文件和不存在的文件夹。

它的工作原理就像shutil.move() ,但是现有的文件只能被覆盖,而不shutil.move()删除。

 import os import shutil def moverecursively(source_folder, destination_folder): basename = os.path.basename(source_folder) dest_dir = os.path.join(destination_folder, basename) if not os.path.exists(dest_dir): shutil.move(source_folder, destination_folder) else: dst_path = os.path.join(destination_folder, basename) for root, dirs, files in os.walk(source_folder): for item in files: src_path = os.path.join(root, item) if os.path.exists(dst_file): os.remove(dst_file) shutil.move(src_path, dst_path) for item in dirs: src_path = os.path.join(root, item) moverecursively(src_path, dst_path)