【问题标题】:Iterate over two files Python遍历两个文件 Python
【发布时间】:2021-03-08 22:01:22
【问题描述】:

我有两个 CSV 文件,一个是机场列表,第二个是将机场的区域代码转换为区域名称的区域文件。但是机场也已经给出了一个自治市,所以我想检查自治市何时与该地区相同。 我想出了这个,但它很慢,我当然不能使用 zip,因为它不是线性的。 每个机场在区域文件中找到它的区域代码,然后将区域名称与市镇进行比较。

import csv
with open('airports.csv', 'r', encoding='utf-8') as airport_csv:
        airport_csv_reader = csv.DictReader(filter(lambda row: row[0]!='#', airport_csv))
        for airport in airport_csv_reader:
            with open('regions.csv', 'r', encoding='utf-8') as regions_csv:
                regions_csv = csv.DictReader(filter(lambda row: row[0]!='#', regions_csv))
                for region in regions_csv:
                    if region['code'] == airport['iso_region']:
                        if region['name'] == airport['municipality']:
                            print('ident', airport['ident'], 'municipality', airport['municipality'], 'region', region['name'])

【问题讨论】:

  • 我们对您的文件大小一无所知,但速度慢的原因是您正在检查所有内容。 (for airport in ...for region in ...)。这与airport.csvregions.csv 的大小成比例。最简单的解决方案,使用pandas,使用read_csv 加载csv 并使用merge 合并数据。

标签: python python-3.x csv


【解决方案1】:

你可以这样做:

import csv

with open('regions.csv', 'r', encoding='utf-8') as f:                
  regions_csv_reader = csv.DictReader(filter(lambda row: row[0]!='#', f))
  seen = [(row['code'], row['name']) for row in regions_csv_reader]

with open('airports.csv', 'r', encoding='utf-8') as f:
  airport_csv_reader = csv.DictReader(filter(lambda row: row[0]!='#', f))
    for row in airport_csv_reader:        
      if (row['iso_region'], row['municipality']) in seen:
        print('ident', row['ident'], 'municipality', row['municipality'], 'region', row['municipality'])

但是,当您查看机场直辖市与地区名称相同的行时,我没有看到将地区名称/市镇打印两次的意义。

【讨论】:

  • 完美运行,是的,我意识到我不需要打印两次。
【解决方案2】:

我认为这很慢的原因是重复打开文件,请考虑在开始 for 循环之前加载“regions.csv”文件:

regions_csvFile = open('regions.csv', 'r', encoding='utf-8')
regions_csv = csv.DictReader(filter(lambda row: row[0]!='#', regions_csv))
regions_csvFile.close()

然后是其余的代码

【讨论】:

  • 我自己试过这个,我认为它不起作用,因为 DictReader 一次只加载一行,所以它只留下一个区域的循环。但是,下面的解决方案可以工作,因为它将每一行加载到一个保留的列表中。
  • 啊甜蜜!不知道它是这样工作的,很高兴你找到了解决方案。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-04-23
  • 2018-10-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2015-05-25
相关资源
最近更新 更多