如何按行的前3个字符对文本文件进行分组?

时间:2013-11-20 09:54:46

标签: python group-by itertools

我有一个包含三列的列表:ID,经度,纬度:


我的文本文件的一部分:

AFJ.SPZ.IR.8    46.84   38.463
AKL.SPZ.IR.11   46.691  38.399
AKL.SPZ.IR.12   46.722  38.407
AFJ.SPZ.IR.3    46.812  38.433
AFJ.SPZ.IR.8    46.84   38.463
AKL.SPZ.IR.11   46.691  38.399
AKL.SPZ.IR.12   46.722  38.407
AKL.SPZ.IR.13   46.654  38.404
AKL.SPZ.IR.25   46.699  38.442
AKL.SPZ.IR.3    46.812  38.433
AKL.SPZ.IR.8    46.84   38.463
ALA.SPZ.IR.3    46.812  38.433
ANAR.BHZ.IR.8   46.84   38.463
ANJ.SPZ.IR.13   46.654  38.404
ANJ.SPZ.IR.18   46.662  38.399
ANJ.SPZ.IR.3    46.812  38.433
BST.SPZ.IR.1    46.732  38.457
BST.SPZ.IR.10   46.707  38.448
BST.SPZ.IR.11   46.691  38.399
BST.SPZ.IR.12   46.722  38.407

我想对具有相同first3字符的id的lon和lat执行一个函数。 我的代码:

from itertools import groupby

with open('coors1.txt') as fin:
    lines = (line.split() for line in fin)
    for l in lines:
        a=l[0].split(".")
        for key, items in groupby(l,a):
            print (items)

    TypeError: 'str' object is not callable

为什么groupby不理解str?

1 个答案:

答案 0 :(得分:0)

  1. 您需要在应用groupby
  2. 之前对数据进行排序
  3. 您需要将密钥指定为函数,而不是字符串

    from itertools import groupby
    with open('Input.txt') as fin:
        lines = sorted([line.rstrip() for line in fin])
    for item, grp in groupby(lines, key = lambda x:x.split(".")[0]):
        print item, list(grp)
    
  4. <强>输出

    AFJ ['AFJ.SPZ.IR.3    46.812  38.433', 'AFJ.SPZ.IR.8    46.84   38.463', 'AFJ.SPZ.IR.8    46.84   38.463']
    AKL ['AKL.SPZ.IR.11   46.691  38.399', 'AKL.SPZ.IR.11   46.691  38.399', 'AKL.SPZ.IR.12   46.722  38.407', 'AKL.SPZ.IR.12   46.722  38.407', 'AKL.SPZ.IR.13   46.654  38.404', 'AKL.SPZ.IR.25   46.699  38.442', 'AKL.SPZ.IR.3    46.812  38.433', 'AKL.SPZ.IR.8    46.84   38.463']
    ALA ['ALA.SPZ.IR.3    46.812  38.433']
    ANAR ['ANAR.BHZ.IR.8   46.84   38.463']
    ANJ ['ANJ.SPZ.IR.13   46.654  38.404', 'ANJ.SPZ.IR.18   46.662  38.399', 'ANJ.SPZ.IR.3    46.812  38.433']
    BST ['BST.SPZ.IR.1    46.732  38.457', 'BST.SPZ.IR.10   46.707  38.448', 'BST.SPZ.IR.11   46.691  38.399', 'BST.SPZ.IR.12   46.722  38.407']