@piokuc 的回答很好;这是一个简单的解决方案,对于初学者来说应该很容易理解,而无需进入 Counter 的标准库。
您要查找的结果由一组两个(有序)值构成,每个值与一个唯一标签(date:ip 值)相关联。在 Python 中,此类任务的基本数据结构是 dict(字典)。
最好在打开文件时确保在不再需要它们时关闭它们。我将为此使用with 语句;如果您对它的工作原理感兴趣,this is a good resource,但如果您想不通,请记住,一旦 with 块结束,您正在使用的文件 将被关闭自动。
这是代码 - 请记住,您从文件中读取的所有内容都是字符,这意味着您必须在对数字执行任何类型的数学运算之前适当地转换数字:
result = {} # Create your empty dict
with open('full_megalog.txt', 'r') as file: # Open your input file
for line in file: # In each line of the file:
date_ip, num1, num2 = line.split() # 1: Get key and 2 values
if date_ip in result: # 2: Check if key exists
result[date_ip][0] += int(num1) # 3a: If yes, add num1, num2
result[date_ip][1] += int(num2) # to current sum.
else: # 3b: If no, add the new key
result[date_ip] = int(num1), int(num2) # and values to the dict
现在您有一个result 字典,它将num1 和num2 的总和与每个对应的date_ip 相关联。您可以使用result[date_ip] 访问(num1, num2) 元组,并且可以使用result[date_ip][0] 和result[date_ip][1] 单独访问这些值。
如果您想以原始格式编写此代码,则必须将每个键和两个值与一个空格字符连接在一起;冗长、容易评论的方式可能是这样的:
with open('condensed_log_file.txt', 'w') as out: # open the output file;
for date_ip in result: # loop through the keys;
out.write( # write to the logfile:
' '.join( # joined by a space char,
(date_ip, # the key (date_ip);
str(result[date_ip][0]), # the 1st value (num1);
str(result[date_ip][1])) # & the 2nd value (num2).
)
我很好奇 piokuc 非常整洁干净的方法与我自己的幼稚方法的性能比较。这没有打印和输出文件写入语句:
>>> from timeit import timeit
>>> a = open("airthomas.py", "r")
>>> a = a.read()
>>> p = open("piokuc.py", "r")
>>> p = p.read()
>>> timeit(p)
115.33428788593137
>>> timeit(a)
103.95908962552267
所以,如果您需要在大量小文件上运行它,使用Counter() 可能会慢一点。当然,您可能只需要在一个或几个非常大的文件上运行它——在这种情况下,请自己进行测试! ;P