首页 > 解决方案 > 找不到文件错误 - 如何处理该错误

问题描述

我需要将文件从临时目录复制到新的子目录。它必须在一个函数中完成。我定义了新目录,检查它们是否存在。源目录包含多个文件。由于这些是临时目录,我认为我不使用相对路径。我有一个函数不断给我这个错误:

---------------------------------------------------------------------------
FileNotFoundError                         Traceback (most recent call last)
<ipython-input-24-c7f9666ed031> in <module>()
     38 
     39 split_size = .9
---> 40 split_data(CAT_SOURCE_DIR, TRAINING_CATS_DIR, TESTING_CATS_DIR, split_size)
     41 split_data(DOG_SOURCE_DIR, TRAINING_DOGS_DIR, TESTING_DOGS_DIR, split_size)
     42 

2 frames
/usr/lib/python3.6/genericpath.py in getsize(filename)
     48 def getsize(filename):
     49     """Return the size of a file, reported by os.stat()."""
---> 50     return os.stat(filename).st_size
     51 
     52 

FileNotFoundError: [Errno 2] No such file or directory: '3913.jpg'

这是我的功能。我什至尝试添加一行,告诉函数不要复制不存在的文件。

def split_data(SOURCE, TRAINING, TESTING, SPLIT_SIZE):
    source_files = [f for f in os.listdir(SOURCE) if os.path.getsize(f) > 0]
    source_files = [f for f in os.listdir(SOURCE) if os.path.exists(f)]
    random.shuffle(source_files)
    total = len(source_files)
    to_training = source_files[0: int(total * SPLIT_SIZE)]
    to_test = source_files[int(total * SPLIT_SIZE):]
    for f in to_training:
      copyfile(os.path.join(SOURCE, f), TRAINING)
    for f in to_test:
      copyfile(os.path.join(SOURCE, f), TESTING)
    assert len(source_files) == len(to_training) + len(to_test)

当我检查源目录的长度时,它充满了图像,然后我检查我的文件夹是否已使用 os.isdir() 正确创建,所以它们是。我不知道如何解决这个问题。请帮忙。

标签: python

解决方案


您没有传递有效的路径os.path.getsize,只是某个目录中的文件名。从函数的文档中os.listdir

返回一个列表,其中包含路径给定的目录中条目的名称。

这些名称不是路径。要获得文件的正确路径,您必须将传递给的参数加入每个元素os.listdir

source_files = [f for f in os.listdir(SOURCE) if os.path.getsize(os.path.join(SOURCE, f)) > 0]

但是,因为您基本上是os.stat在调用目录中的每个文件,所以使用它会更有效率os.scandir。从文档中

使用 scandir() 代替 listdir() 可以显着提高还需要文件类型或文件属性信息的代码的性能,因为如果操作系统在扫描目录时提供了这些信息,os.DirEntry 对象就会公开这些信息。

这意味着你可以这样做:

source_files = [f.path for f in os.scandir(SOURCE) if f.stat().st_size > 0]

此表单还将设置source_files为文件路径列表,因此您无需os.path.join稍后调用。如果你真的只想要文件名,你可以在理解中f.path替换为。f.name您可以找到更多关于f.os.DirEntry


推荐阅读