【问题标题】:Python loop through two files, do computation, then output 3 filesPython循环遍历两个文件,进行计算,然后输出3个文件
【发布时间】:2011-10-02 21:59:15
【问题描述】:

我有 2 个制表符分隔的文件 例如:

文件1:

12  23  43  34
433  435  76  76

文件2:

123  324  53  65
12  457  54  32

我想遍历这两个文件,将 file1 的每一行与 file2 进行比较,反之亦然。 例如,如果 file1 中第 1 行的第 1 个编号与文件 2 中第 2 行的第 1 个编号相同: 我想从 file1 的第一行放入一个名为 output 的文件中。 然后我想将 file1 中在文件 2 中找不到匹配项的所有行放入新文件中 以及 file2 中在新文件中的 file1 中未找到匹配项的所有行。

到目前为止,我已经能够找到匹配的行并将它们放入一个文件中,但我无法将不匹配的行放入 2 个单独的文件中。

one=open(file1, 'r').readlines()
two=open(file2, 'r').readlines()
output=open('output.txt', 'w')
count=0
list1=[]    #list for lines in file1 that didn't find a match 
list2=[]    #list for lines in file2 that didn't find a match
for i in one:
    for j in two:
        columns1=i.strip().split('\t')
        num1=int(columns1[0])
        columns2=j.strip().split('\t')
        num2=int(columns2[0])
        if num1==num2:
           count+=1
           output.write(i+j)
        else:
           list1.append(i)        
           list2.append(j)

我在这里遇到的问题是 else 部分。 谁能告诉我正确和更好的方法,我将不胜感激。

编辑:感谢大家的快速回复 我要寻找的 3 个输出是:

Output_file1: #2个文件的匹配结果

12 23 43 34 #line from file1
12 457 54 32 #line from file2

Output_file2: #lines from the first file that didn't find a match

433 435 76 76

Output_file3: #lines from the second file that didn't find a match

123 324 53 65

【问题讨论】:

  • 第一个文件第一行的第一个值和第二个文件第二行的第一个值?
  • 要了解您要执行的操作的逻辑,您能否为上面列出的两个输入文件提供您想要的三个输出文件?
  • @Artsiom Rudzenka:对不起,我想说的是,在我给出的示例中,这是定义匹配的条件或逻辑。

标签: python file loops


【解决方案1】:

我建议你使用 csv 模块来读取你的文件(你可能不得不乱用方言,请参阅http://docs.python.org/library/csv.html 寻求帮助:

import csv
one = csv.reader(open(file1, 'r'), dialect='excell')
two = csv.reader(open(file2, 'r'), dialect='excell')

那么您可能会发现像这样同时沿两个文件的行“压缩”更容易(请参阅http://docs.python.org/library/itertools.html#itertools.izip_longest):

import itertools
file_match = open('match', 'w')
file_nomatch1 = open('nomatch1', 'w')
file_nomatch2 = open('nomatch2', 'w')
for i,j in itertools.izip_longest(one, two, fillvalue="-"):
    if i[0] == j[0]:
        file_match.write(str(i)+'\n')
    else:
        file_nomatch1.write(str(i)+'\n')
        file_nomatch2.write(str(j)+'\n') 
        # and maybe handle the case where one is "-"

我重读了这篇文章并意识到您正在寻找两个文件中任意两行之间的匹配项。也许有人会发现上面的代码很有用,但它不能解决你的特定问题。

【讨论】:

  • 谢谢帕特,我找到了这个例子,是的,它只按行搜索,但还是谢谢。
  • 与其“玩弄方言”(顺便说一句,我不相信有'excell'这样的方言;应该是'excel'),他可以简单地使用@987654327 @.
【解决方案2】:

我建议使用set operation

from collections import defaultdict

def parse(filename):
    result = defaultdict(list)
    for line in open(filename):
        # take the first number and put it in result
        num = int(line.strip().split(' ')[0])
        result[num].append(line)  
    return result

def select(selected, items):
    result = []
    for s in selected:
        result.extend(items[s])
    return result

one = parse('one.txt')
two = parse('two.txt')
one_s = set(one)
two_s = set(two)
intersection = one_s & two_s
one_only = one_s - two_s
two_only = two_s - one_s

one_two = defaultdict(list)
for e in one: one_two[e].extend(one[e])
for e in two: one_two[e].extend(two[e])

open('intersection.txt', 'w').writelines(select(intersection, one_two))
open('one_only.txt', 'w').writelines(select(one_only, one))
open('two_only.txt', 'w').writelines(select(two_only, two))

【讨论】:

    【解决方案3】:

    认为这不是最好的方法,但它对我有用,而且看起来很容易理解:

    # Sorry but was not able to check code below
    def get_diff(fileObj1, fileObj2):
        f1Diff = []
        f2Diff = []
        outputData = []
        # x is one row
        f1Data = set(x.strip() for x in fileObj1)
        f2Data = set(x.strip() for x in fileObj2)
        f1Column1 = set(x.split('\t')[0] for x in f1Data)
        f2Column1 = set(x.split('\t')[0] for x in f2Data)
        l1Col1Diff = f1Column1 ^ f2Column1
        l2Col1Diff = f2Column1 ^ f1Column1
        commonPart = f1Column1 & f2column1
        for line in f1Data.union(f2Data):
            lineKey = line.split('\t')[0]
            if lineKey in common:
                outputData.append(line)
            elif lineKey in l1ColDiff:
                f1Diff.append(line)
            elif lineKey in l2ColDiff:
                f2Diff.append(line)
        return outputData, f1Diff, f2Diff
    
    outputData, file1Missed, file2Missed = get_diff(open(file1, 'r'), open(file2, 'r'))
    

    【讨论】:

    • 有没有办法一次输出所有三个文件(outputData、file1Missed 和 file2Missed)?
    • @user839145 我已经修改了我的代码以一次返回所有三个列表-m但我无法检查它。如果您有任何问题,请告诉我
    • 非常感谢Artsiom,我希望有办法修改你的代码的最后一个版本,因为我需要做更多的比较,而不仅仅是比较值。而且我对set操作不是很熟悉。我会研究它。
    • Set 不是一种操作,它是一种数据类型:docs.python.org/library/stdtypes.html#set-types-set-frozenset。至于代码 - 是的,我的上一个版本也可以修改,你可以联系我,我会尽力提供帮助。
    【解决方案4】:

    我认为这段代码符合你的目的

    one=open(file1, 'r').readlines()
    two=open(file2, 'r').readlines()
    output=open('output.txt', 'w')
    
    first = {x.split('\t')[0] for x in one}
    second = {x.split('\t')[0] for x in two}
    common = first.intersection( second )
    list1 = filter( lambda x: not x.split('\t')[0] in common, one )
    list2 = filter( lambda x: not x.split('\t')[0] in common, two )
    res1 = filter( lambda x: x.split('\t')[0] in common, one )
    res2 = filter( lambda x: x.split('\t')[0] in common, two )
    count = len( res1 )
    for x in range(count):
        output.write( res1[x] )
        output.write( res2[x] )
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-12
      • 2013-09-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多