如何使用python创建带有名称的多个文件夹,并将多个zip提取到每个不同的文件夹?

时间:2019-06-07 17:35:17

标签: python directory zip extract

我无法为包含不同栅格数据的许多不同zip文件夹创建许多不同的目录,然后以干净的脚本将所有zip提取到新文件夹中。

我已经用我的代码完成了我的任务,这很长而且很凌乱。我需要具有标记为NE34_ENE35_E等的文件夹,然后在这些目录中,我需要诸如N34_24N34_25等的子文件夹,这些子文件夹将栅格数据将被提取到。我有100多个zip文件需要提取并放在子文件夹中。

对我制作目录的方式进行了一些更改之后,这是我的脚本示例。

我的文件结构如下:

N\\N36_E\\N36_24
N\\N36_E\\N35_25
... etc.

Zipfile名称:

n36_e024_1arc_v3_bil.zip
n36_e025_1arc_v3_bil.zip
n36_e026_1arc_v3_bil.zip
... etc.

用于创建目录结构的Python代码:

import os

#Create Sub directories for "NE36_"
pathname1 = "NE36_"
pathname2 = 24
directory = "D:\\Capstone\\Test\\N36_E\\" + str(pathname1) + str(pathname2)
while pathname2 < 46:
    if not os.path.exists(directory):
        os.makedirs(directory)
    pathname2 += 1
    directory = "D:\\Capstone\\Test\\N36_E\\" + str(pathname1) + str(pathname2)

#Create Sub directories for "NE37_"
pathname1 = "NE37_"
pathname2 = 24
directory = "D:\\Capstone\\Test\\N37_E\\" + str(pathname1) + str(pathname2)
while pathname2 < 46:
    if not os.path.exists(directory):
        os.makedirs(directory)
    pathname2 += 1
    directory = "D:\\Capstone\\Test\\N37_E\\" + str(pathname1) + str(pathname2)

1 个答案:

答案 0 :(得分:1)

import glob, os, re, zipfile

# Setup main paths.
zipfile_rootdir = r'D:\Capstone\Zipfiles'
extract_rootdir = r'D:\Capstone\Test'

# Process the zip files.
re_pattern = re.compile(r'\A([a-zA-Z])(\d+)_([a-zA-Z])0{0,2}(\d+)')

for zip_file in glob.iglob(os.path.join(zipfile_rootdir, '*.zip')):

    # Get the parts from the base zip filename using regular expressions.
    part = re.findall(re_pattern, os.path.basename(zip_file))[0]

    # Make all items in part uppercase using a list comprehension.
    part = [item.upper() for item in part]

    # Create a dict of the parts to make useful parts to be used for folder names.
    # E.g. from ['N', '36', 'E', '24']
    folder = {'outer': '{0}{1}_{2}'.format(*part),
              'inner': '{0}{2}{1}_{3}'.format(*part)}

    # Build the extraction path from each part.
    extract_path = os.path.join(extract_rootdir, folder['outer'], folder['inner'])

    # Perform the extract of all files from the zipfile.
    with zipfile.ZipFile(zip_file, 'r') as zip:
        zip.extractall(extract_path)

2个主要设置来设置值,即:

  1. zipfile_rootdir是zip文件所在的位置。
  2. extract_rootdir是提取到的位置。

字符串前的r被视为原始字符串, 因此不需要反斜杠转义。

正则表达式被编译并用于提取 zip文件名称中的文本用于 提取路径。

来自zip文件:

n36_e024_1arc_v3_bil.zip

使用正则表达式提取零件序列:

n, 36, e, 24

每个项目都大写并用于创建字典 名为folders的键和值:

'outer': 'N36_E'
'inner': 'NE36_24'

extract_path将通过加入来存储完整路径 extract_rootdirfolder['outer']folder['inner']

最后,使用上下文管理器通过with提取zip文件。


正则表达式:

re_pattern = re.compile(r'\A([a-zA-Z])(\d+)_([a-zA-Z])0{0,2}(\d+)')

之前的正则表达式模式的编译 循环是为了避免模式的多次编译 在循环。 在字符串前使用r是为了通知Python 该字符串应解释为原始字符串 即没有反斜杠转义。 原始字符串对于正则表达式很有用,因为 模式使用反斜杠转义。

正则表达式模式:

\A([a-zA-Z])(\d+)_([a-zA-Z])0{0,2}(\d+)

要使用的正则表达式的字符串:

n36_e024_1arc_v3_bil.zip
  1. \A仅在字符串的开头匹配。 这是一个锚点,与任何字符都不匹配。
  2. ([a-zA-Z])匹配任何字母字符。 []与其中的任何字符匹配。 az范围内的任何字符,以及 AZ已匹配。 n将被匹配。 封闭的()存储捕获到的组 返回的序列。现在序列是n,
  3. (\d+)匹配1位或更多位数字。 \d是任何数字 和+告诉它继续匹配更多内容。 序列变为n, 36,
  4. _是文字的,并且由于()没有包含它,因此它 匹配,但未添加到序列中。
  5. ([a-zA-Z])与第2点相同。 序列变为n, 36, e,
  6. 0{0,2}匹配一个零0,零至2倍{0,2}。 没有(),因此未添加到序列中。
  7. (\d+)与第3点相同。 序列变为n, 36, e, 24
  8. 字符串的其余部分作为模式被忽略 已经到尽头了。这就是\A是 使用该模式无法从任何地方开始 继续到不需要的字符串的末尾。

格式化:

序列大写后为N, 36, E, 24 通过列表理解。

  1. 模式{0}{1}_{2}已排序0, 1, 2, 因此0为N,1为36和2为E N36_E_是模式中的文字。
  2. 模式{0}{2}{1}_{3}已排序 0, 2, 1, 3。 0是N,2是E,1是36 而3是24成为NE36_24

参考文献:

  • Python 2:

  • Python 3: