2010-11-24 88 views
1

这是我第一次将代码碎片拼凑起来,形成我需要的实用程序(我是一位贸易设计师),虽然我觉得我是关闭,我无法使以下工作。Python - 在多个目录中搜索文件和ZIP

我经常需要压缩具有.COD扩展名的文件,这些文件位于我创建的目录结构中。作为一个例子,该结构可以是这样的:

(单根文件夹) - >(多个文件夹) - >(两个文件夹) - >(一个文件夹) - > COD文件

我需要ZIP将所有COD文件放入COD.zip中,并将该zip文件放置在当前文件的上方一个目录中。文件夹结构是这样的,例如完成时:

导出文件夹 - > 9800文件夹 - > 6文件夹 - > OTA文件夹(+新COD.zip) - > COD文件

我的问题 -

首先,它创建的COD.zip似乎适合其中的COD文件,但是当我解压缩它时,内部只有1.cod,但该ZIP的文件大小是所有COD压缩在一起的大小。

秒,我需要COD文件压缩W/O任何文件夹结构 - 直接在COD.zip内。目前,我的脚本创建了一个完整的目录结构(以“users/mysuername/etc etc”开头)。

任何帮助将不胜感激 - 和解释,甚至更好,因为我想学习:)

感谢。

import os, glob, fnmatch, zipfile 


def scandirs(path): 
for currentFile in glob.glob(os.path.join(path, '*')): 
    if os.path.isdir(currentFile): 
     scandirs(currentFile) 
    if fnmatch.fnmatch(currentFile, '*.cod'): 
      cod = zipfile.ZipFile("COD.zip","a") 
      cod.write(currentFile) 


scandirs(os.getcwd()) 

回答

1

对于问题#1,我觉得你的问题很可能是这一部分:

cod = zipfile.ZipFile("COD.zip","a") 
cod.write(currentFile) 

你正在创建一个新的压缩(并且可能覆盖现有的),每次你去写新文件。相反,您要为每个目录创建一次zip,然后重复追加(参见下面的示例)。

对于问题#2,你的问题是,当你将它写入档案时,你可能需要将文件名变平。一种方法是使用os.chdir将CD复制到scandirs的每个目录中。更简单的方法是使用os.path模块分割文件路径并获取基本名称(不带路径的文件名),然后可以使用第二个参数cod.write来更改放入实际zip文件的文件名(请参阅示例下面)。

import os, os.path, glob, fnmatch, zipfile 

def scandirs(path): 

    #zip file goes at current path, then up one dir, then COD.zip 
    zip_file_path = os.path.join(path,os.path.pardir,"COD.zip") 
    cod = zipfile.ZipFile(zip_file_path,"a") #NOTE: will result in some empty zips at the moment for dirs that contain no .cod files 

    for currentFile in glob.glob(os.path.join(path, '*')): 
     if os.path.isdir(currentFile): 
     scandirs(currentFile) 
     if fnmatch.fnmatch(currentFile, '*.cod'): 
     cod.write(currentFile,os.path.basename(currentFile)) 

    cod.close() 
    if not cod.namelist(): #zip is empty 
     os.remove(zip_file_path) 

scandirs(os.getcwd()) 

因此创建zip文件一次,反复附加到它,同时展开文件名,然后关闭它。您还需要确保您致电接近,否则您可能无法写入所有文件。

我没有一个很好的方法来测试这个地方在这一刻,所以随时尝试一下,并报告回来。我相信我可能会破坏一些东西。 ;-)

+0

我担心这会让太多的.zip文件句柄一次打开。你可以决定改变你的递归一下,先递归遍历所有的目录,并且只有当没有更多的目录时,然后执行当前目录中的所有文件,而不是一次性混合执行文件和目录。 – 2010-11-24 23:54:01

1

以下代码具有相同的效果,但更易于重用,并且不会创建多个zip文件。

import os,glob,zipfile 

def scandirs(path, pattern): 
    result = [] 
    for file in glob.glob(os.path.join(path, pattern)): 
     if os.path.isdir(file): 
      result.extend(scandirs(file, pattern)) 
     else: 
      result.append(file) 
    return result 


zfile = zipfile.ZipFile('yourfile.zip','w') 
for file in scandirs(yourbasepath,'*.COD'): 
    print 'Processing file: ' + file 
    zfile.write(file)     # folder structure 
    zfile.write(file, os.path.split(file)[1]) # no folder structure 

zfile.close()