首页 > 解决方案 > 如何使用python3将路径中的文件夹移动到Windows中的另一个路径?

问题描述

我需要一个脚本来移动源文件夹中的所有内容并创建/替换到目标文件夹,而不删除目标中的任何现有文件/文件夹。test1 文件夹的内容将是一个 html 文件以及一些 png 格式的图像。

源路径:C:\Users\USERNAME\Documents\LocalFolder\reports\v2
源文件夹名称test1

目标路径:T:\remoteReports\myTests 复制时要创建的路径: \LocalFolder\reports\v2
从源复制到目标的文件夹test1

destinaton 中的最终路径: T:\remoteReports\myTests\LocalFolder\reports\v2\test1

我从堆栈溢出中获取了一段代码并将其用于我的应用程序,但运行脚本并没有在目标中创建路径和文件夹。

import time
import os
import random
import shutil
import pathlib
def move_files(root_src_dir,root_dst_dir):
print(root_src_dir)
print(root_dst_dir)
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):
        # in case of the src and dst are the same file
            if os.path.samefile(src_file, dst_file):
                continue
    os.remove(dst_file)
    shutil.move(src_file, dst_dir) 
 srcPath = os.path.join("C:", "Users", os.getlogin(),"Documents", "LocalFolder", "v2", "test1")
 dstPath = os.path.join("T:", "remoteReports", "myTests", "LocalFolder", "v2", "test1")
 move_files(srcPath,dstPath )

如果有人可以指导我,这将很有帮助!

标签: pythonpython-3.x

解决方案


您可以使用pathlib将所有文件从一个文件夹复制到另一个文件夹:

from pathlib import Path
from shutil import copy

src = Path(r"C:\Users\USERNAME\Documents\LocalFolder\reports\v2")
dst = Path(r"T:\remoteReports\myTests\LocalFolder\reports\v2")
for file in src.iterdir():
    if file.is_file() and not (dst / file.name).is_file():
        copy(file, dst)

如果要复制包括子目录及其内容的整个树,可以申请os.walk()

from pathlib import Path
from os import walk
from shutil import copy

src = Path(r"C:\Users\USERNAME\Documents\LocalFolder\reports\v2")
dst = Path(r"T:\remoteReports\myTests\LocalFolder\reports\v2")
for dir_name, _, filenames in walk(src):
    src_path = Path(dir_name)
    dst_path = dst / src_path.relative_to(src)
    if not dst_path.is_dir():
        dst_path.mkdir()
    for file in filenames:
        dst_file = dst_path / file
        if not dst_file.is_file():
            copy(src_path / file, dst_path)

或者您可以从我首先建议的代码中创建函数并递归使用它:

from pathlib import Path
from shutil import copy

def copy_folder(src_path, dst_path):
    if not dst_path.is_dir():
        dst_path.mkdir()
    for file in src_path.iterdir():
        if file.is_dir():
            copy_folder(file, dst_path / file.relative_to(src_path))  # recursion
        elif file.is_file() and not (dst_path / file.name).is_file():
            copy(file, dst_path)

src = Path(r"C:\Users\USERNAME\Documents\LocalFolder\reports\v2")
dst = Path(r"T:\remoteReports\myTests\LocalFolder\reports\v2")
copy_folder(src, dst)

但是您实际上并不需要手动实现所有这些,因为shutil.copytree()已经存在并且与我之前提供的所有选项完全相同。重要提示:如果目标路径中的目录已经存在,您应该传递dirs_exist_ok参数以不引发异常。

from shutil import copy, copytree
from os.path import exists

src = r"C:\Users\USERNAME\Documents\LocalFolder\reports\v2"
dst = r"T:\remoteReports\myTests\LocalFolder\reports\v2"
copytree(src, dst, copy_function=lambda s, d: not exists(d) and copy(s, d), dirs_exist_ok=True)

这里我使用lambda了 which check does file already exists 来不覆盖它,如果你不关心文件是否会被覆盖,你可以省略这个参数。


如果要移动所有文件,可以传递shutil.move()copy_function

from shutil import move, copytree
...
copytree(src, dst, copy_function=move, dirs_exist_ok=True)

它将移动所有文件,但保留树目录。如果要复制所有目录树并将其从源中删除,可以调用shutil.copytree()and shutil.rmtree()

from shutil import copytree, rmtree
...
copytree(src, dst, dirs_exist_ok=True)
rmtree(src)

推荐阅读