我想在这个问题前面加上这样一个事实,即我已经完成了对python时间复杂度和数据结构的研究,可以加快速度。
但是,我正在努力想出一种有效的方法来检查一组250万行文件的值。到目前为止,我考虑过的一个解决方案是使用列表推导。
目前,我正试图通过以下方式处理:
def getTotalVolumeByCounty(fileName, counties):
values = []
with open(fileName) as csvFile:
csvReader = csv.reader(csvFile)
headers = next(csvReader)
for row in csvReader:
i = 0
while i < len(counties):
if row[9] == counties[i]:
values[i] += int(row[22])
break
return values
如果你愿意,那就是“传统”的方式。将一个列表中的每个值与另一个列表中的当前值进行比较。显然,就时间复杂性而言,这是不利的。
如前所述,我已经考虑过使用列表推导 - 但这些如何实际节省时间?列表理解是我当前尝试的唯一替代方案吗?
这些天250万行并不是很多,但是你不太正常工作的代码将每行检查乘以工作方面的县数量,这将使它变得非常慢。如果我们使用你所在国家的中间字典,我们可以这样做得更快:
def get_total_volume_by_county(file_name, counties):
county_volume_map = {county: 0 for county in counties}
with open(file_name) as csv:
csv_reader = csv.reader(csv)
headers = next(csv_reader)
for row in csv_reader:
county_volume_map[row[9]] += row[22]
return county_volume_map
如果您真的只想要卷列表,可以在最后将其转换回来,但是县到卷的地图可能更有用。
根据OP上的评论主题,我将在这里添加一个建议。
处理大量数据时,首先以某种方式对数据进行排序然后使用二进制搜索等方法来查找数据块通常会更有效。
例如,您提到要将一个列表中的项目与第二个列表中的项目进行比较。出于此目的,我将假设第一个列表(列表A)的大小很小而第二个列表(列表B)很大。
如果列表B中的项目按某个键排序,例如,县名称(假设所有县都有唯一名称),您可以使用Binary Search Algorithm在县的条目块中查找随机(基本上)项目,然后根据任何给定县的条目数量,您可以执行2个循环来查找上限和下限或另一个二进制搜索或类似的不同键,通过该键将列表排序到原始键的第二位(例如总数volume)将为您提供一个列表,其中列出了与您确定的某些指标相匹配的项目。
如果数据尚未排序,则可能值得对其进行排序,因为Heapsort或Quicksort的时间复杂度最差为O(nlogn),二进制搜索最差为O(logn)。循环遍历列表的时间复杂度可能是O(kn ^ k)或其他东西的顺序,如果你要绘制图形,那将会好多倍。
至于你问题的最后一部分,列表理解只是语法糖,并没有做任何特别奇特的事情。
tldr;通过一些唯一标识符对数据进行排序,我建议使用Heapsort作为就地,通用,因为你可以提供比较函数,它可以使用它,你可以在Python中查找迭代实现。然后使用二进制搜索有效地查找项目。
希望这可以帮助!
完全基于你的功能名称和它的签名,我将假设你只是试图按国家分组销售总量,其中countries
是你感兴趣的国家的列表。最直接Python中的前进方式是使用dict
计数。使用dict
对象惯用分组。在这种情况下,你的dict
也将作为“set”,因为我们将使用0
为每个国家初始化dict。然后在增加相应的值之前检查国家是否在dict中。
def get_total_volume_by_country(file_name, counties):
volume_by_country = dict.fromkeys(countries, 0)
with open(file_name) as csv_file:
csv_reader = csv.reader(csv_file)
headers = next(csv_reader)
for row in csv_reader:
country = row[9] # presumably country name
if country in volume_by_country:
volume_by_country[country] += int(row[22]) # volume presumably
return volume_by_country