我对python相当陌生,我想知道如何将一个文件从一个位置复制粘贴到另一个位置,首先检查复制的文件是否存在于目标文件夹中?
我想检查这个文件是否存在的原因是这个脚本将被放在一个任务调度程序中,并按照一个既定的时间表运行,所以我不想每次都复制所有东西,只复制目标文件夹中不存在的那些文件?
提前谢谢!
- os.path.exists(/some/path/)
- FWIW,我认为几乎总有比os.path.exists更好的方法来处理文件的创建/删除/使用。在大多数情况下,有另一个模块可以更优雅地处理它(正如我在回答中使用glob比较两个列表时使用的),如果没有,try/catch可以更好地防止竞争条件。我想不出我写过的任何使用os.path.exists的脚本,我不能重写以使用glob更好的功能。
- @adsmith除非您有一些安全问题,否则没有理由不使用os.path.exist
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
| import glob
import os.path
import shutil
SRC_DIR = #your source directory
TARG_DIR = #your target directory
GLOB_PARMS ="*" #maybe"*.pdf" ?
for file in glob.glob(os.path.join(SRC_DIR,GLOB_PARMS)):
if file not in glob.glob(os.path.join(SRC_DIR,GLOB_PARMS)):
shutil.copy(file,TARG_DIR)
else:
print("{} exists in {}".format(
file,os.path.join(os.path.split(TARG_DIR)[-2:]))
# This is just a print command that outputs to console that the
# file was already in directory |
我假设您试图用这个命令发送整个文件夹,否则glob使用非常容易理解的接口。glob.glob *.txt将抓取扩展名为.txt的所有文件,等等。把它调整成你想要的样子应该不会太难。
需要注意的是,文件复制通常涉及竞争条件。基本上,在检查文件是否不在TARG_DIR (if file not in glob.glob(TARG_DIR))和实际复制文件(shutil.copy(file,TARG_DIR))之间要经过一段时间。在这段时间内,文件可能会结束在那里,这将导致shutil.copy覆盖文件。这可能不是您想要的功能,在这种情况下,您应该研究不同的方法。我不知道一个好的没有一些研究,将试图复制一个文件,但返回一个例外,如果该文件已经存在。
正如前面提到的另一个答案,Try/Except块在这里也很有用,如果脚本运行时您没有对目录的写访问权。如果是这样,shutil.copy将返回一个IOError异常。我相信,如果您没有对源目录的读访问权,glob将只返回一个空列表(而源目录将不通过"For"循环提供任何内容,因此不会有任何错误)。
编辑:显然glob的工作方式和我记忆中的不一样,对此我很抱歉。
- 在这种情况下,我不想复制整个文件夹,我想复制文件夹内的内容,PDF文件。
- 这就是它的作用,抱歉我不清楚。glob.glob根据给定的参数返回文件夹的内容列表(例如,glob.glob(TARG_DIR+"\\*.pdf")将返回扩展名为PDF的TARG_DIR文件列表)。
- 下面是我所尝试的,并得到一个错误:import glob import os.path import shutil SRC_DIR ="C:\\Users\\mboyle\\Documents\\Source" TARG_DIR ="C:\\Users\\mboyle\\Documents\\Target" for file in glob.glob(SRC_DIR): if file not in glob.glob(TARG_DIR): shutil.copy(file,TARG_DIR) else: print"exists"
- 这个错误是什么?
- 第10行是shutil.copy(file,TARG_DIR)。是否需要指定文件类型(.pdf)?
- 不。你能帮我粘贴堆栈跟踪吗?
- Traceback (most recent call last): File"C:\Users\mboyle\Desktop\CopyPaste.py", line 10, in shutil.copy(file,TARG_DIR) File"C:\Python27\ArcGIS10.1\lib\shutil.py", line 116, in copy copyfile(src, dst) File"C:\Python27\ArcGIS10.1\lib\shutil.py", line 81, in copyfile with open(src, 'rb') as fsrc: IOError: [Errno 13] Permission denied: 'C:\\Users\\mboyle\\Documents\\Source'
- 无论出于什么原因,您都没有该文件夹的权限。将print(file)置于shutil.copy(file,TARG_DIR)之上可能有助于跟踪它。
- 我检查并完全控制源文件夹和目标文件夹
- 您添加了print行吗?它能打印什么?
- ' C:UsersmboyleDocumentsSource Traceback(最近一次调用last): File"C: UsersmboyleDesktopCopyPaste。",第11行,在<模块> shutil.copy(file,TARG_DIR)文件"C:Python27ArcGIS10.1libshutil。",第116行,在copy copyfile(src, dst)文件"C:Python27ArcGIS10.1libshutil。",第81行,在copyfile中打开(src, 'rb')作为fsrc: IOError: [Errno 13]拒绝的权限:'C:\Users\mboyle\Documents\Source'
- 将打印行更改为print("File is currently %s" % (file))并复制/粘贴整个输出。我不再需要堆栈跟踪——它将是相同的。我想Python没有把你想要的文件拖出来。
- 我试过了,效果不错。唯一的问题是,我不相信它会运行和检查,看看是否相同的文件目前存在或不存在,它只是复制一切。import os import shutil dir_src ="C:\\Users\\mboyle\\Documents\\Source" dir_dst ="C:\\Users\\mboyle\\Documents\\Target" for file in os.listdir(dir_src): src_file = os.path.join(dir_src, file) dst_file = os.path.join(dir_dst, file) shutil.copy(src_file, dst_file)
- 您是对的,代码不会检查文件是否存在。我还发现了我的代码中的错误——glob.glob(this_is_a_dir)没有返回目录的内容,糟糕!glob.glob(root\path\path2\targdir)返回['root\\path\\path2\\targdir','root\\path\\path2\\targdirectory'],这不是您要查找的。我已经更新了我的答案,现在应该可以运行没有bug(至少在我的系统上是这样)
在Python中,经常可以看到,在运行代码时,您会遇到名为exceptions的错误。因此,部署了"yanan8"号。
下面是我日常工作中使用的一段代码,它可以清除目录中的文件,或者跳过不存在的文件。
1 2 3 4 5 6 7 8 9 10
| def DeleteFile(Path_):
"""Deletes saved project AND its corresponding"files" folder."""
try: #deletes the folder
os.remove(Path_)
except OSError:
pass
try: #deletes the file, using some fancy python operations to arrive at the filename
shutil.rmtree(os.path.join(os.path.dirname(Path_),os.path.splitext(os.path.basename(Path_))[0])+"_files", True)
except OSError:
pass |
这是检查文件是否存在的经典示例。您可以尝试复制文件,而不是删除try语句中的内容。如果它失败了,它将继续移动到pass,它将跳过try/catch块。
注意,try/catch可以用来捕获任何异常,也可以用来捕获特定的异常。我已经潦草地写了下来,但还是通读了一遍,以确定那就是你想要的。如果您在catch中有一个特定的错误,并且系统返回了错误类型的错误,那么您的try/catch将不能按照您希望的方式工作。所以,一定。在最好的情况下,要概括。
编码快乐!
编辑:值得注意的是,这个try/catch系统是一种非常python化的处理方法。try/catch非常简单和受欢迎,但是你的情况可能需要一些不同的东西。
编辑:我不确定这是否值得注意,但我意识到我的答案并没有直接告诉您如何检查文件是否存在。相反,它假定它不执行操作,并继续执行操作。如果你遇到了一个问题(例如。,它是存在的,您需要覆盖它),您可以使它自动跳过整个内容,进入下一个。同样,这只是完成相同任务的众多方法之一。
- 函数名和变量名中的大写字母在大多数Python项目中被认为是不好的样式:python.org/dev/peps/pep-0008