【问题标题】:Python Splitting a file into many files and adding in extra infoPython将文件拆分为多个文件并添加额外信息
【发布时间】:2016-03-14 16:00:01
【问题描述】:

我希望拆分 2 个文本文件并将它们组合起来:

所以第一个文件称为“Names.txt”,是一个名称列表。它非常大,因此手动将名称放入下一部分是不行的:

Chloe
Megan
Harry
etc...

第二个文件名为“Attributes.txt”,是一个由 $$$$ 分隔的属性集列表:

attribute1
attribute2
attribute3
$$$$
attribute1
attribute2
etc...

一组属性,每个属性都与第一个文件中的名称相关。但是我不知道每个集合中有多少属性,因为它是随机的。

我想从第一个文件中取出名字,从第二个文件中取出第一组属性并将它们写入一个新文件:

Chloe
attribute1
attribute2
attribute3

然后循环它,以便它使用第二个名称并设置等等......

到目前为止,我有这个代码:

import os
input_file1 = open('Names.txt', 'r')
input_file2 = open('Attributes.txt', 'r')
lines1 = input_file1.readlines()
def group_by_person(some_source):
    buffer = []
    for line in (some_source):
        if line.startswith("$$$$"):
            if buffer: yield buffer
            buffer = [line]
        else:
            buffer.append(line)
    yield buffer
i = 0
name1 = lines1[i]
name2 = name1[:-1]
g = 0
while os.path.exists(name2 + '%s.txt' % g):
    g += 1
with open(name2 + '%s.txt' % g, 'w') as f:
    with input_file2 as source:
        for lines2 in group_by_name(source):
            f.write(lines2[i])
            i += 1

有人可以帮忙吗?

【问题讨论】:

  • 欢迎来到 SO。这是一个质量很好的问题!只缺少一件事:运行代码时会发生什么。显然它不会产生所需的输出,否则你不会问,但它会产生错误的输出、崩溃或烧毁吗? :)
  • 嗨,我收到一个错误“IndexError: list out of range”。它确实编写了一个具有正确名称但具有第二人属性的新文件,并且它根本不循环。
  • 你的错误是什么?如果是崩溃,您通常会获得大量调试信息(例如堆栈跟踪),这些信息对于找出问题所在非常有帮助。
  • 按顺序:阅读、拆分、压缩。加入并写出来。查找它们。
  • 这不是您正在运行的代码。你有一个名为group_by_person 的函数,但你调用了一个名为group_by_name 的函数。请复制并粘贴您的实际代码。谢谢。

标签: python text split writing


【解决方案1】:

我认为这就是您想要实现的目标,如果我错了,请发表评论:

def group_by_person(names_file, attributes_files):
    with open(names_file) as names, open(attributes_files) as attributes:
        for name in names:
            line = [name.strip()]
            for attribute in attributes:
                if attribute.startswith("$$$$"):
                    break
                line.append(attribute.strip())
            print line
            yield line

names_count = {}

for name in group_by_person('Names.txt', 'Attributes.txt'):
    n = name[0]
    names_count[n] = names_count.setdefault(n, 0) + 1
    with open("%s%s.txt" % (n, names_count[n]), 'w') as f:
        f.write('\n'.join(name))

测试结果:

名称.txt:

Chloe
Megan
Chloe

Attributes.txt:

attribute1
attribute2
attribute3
$$$$
attribute4
attribute5
$$$$
attribute6

输出文件:

Chloe1.txt, Megan1.txt, Chloe2.txt

克洛伊1:

Chloe
attribute1
attribute2
attribute3

Megan1.txt

Megan
attribute4
attribute5

Chloe2.txt:

Chloe
attribute6

我相信这是结论性的

最终编辑。

【讨论】:

  • 这不是很接近。 OP 不会在 group_by_persons 中对文件名进行硬编码,并且 OP 还担心输出文件中的名称冲突。
  • 恩,我相信他可以自己改变函数添加额外的参数......这不是重点
  • 当您将迭代编号添加到文件名时,输出文件不会发生冲突。 (除非您将其作为批处理运行,否则您需要一个更强大的系统或记住之前错误的最后一次迭代编号。)
  • OP 的代码有冲突的名称“uniquifiers”,每个名称前移 1,但您已将迭代编号添加到所有名称。
  • 非常感谢 Maresh!像梦一样工作!
【解决方案2】:

您的代码难以阅读和理解。尝试将其拆分为逻辑部分。您为group_by_person 使用了生成器,这是一个很好的解决方案。如何创建相同的生成器来获取人员?之后,您可以使用zip 函数来聚合人员和组。这就是我的意思:

def persons():
    with open('Names.txt', 'r') as f:
        for line in f:
            line = line.rstrip()
            if line: yield line

def groups():
    with open('Attributes.txt', 'r') as f:
        group = []
        for line in f:
            line = line.rstrip()
            if line == '$$$$':
                if group: yield group
                group = []
            else:
                group.append(line)
        if group: yield group


for person, group in zip(persons(), groups()):
    print(person, group)

输出:

Chloe ['attribute1', 'attribute2', 'attribute3']
Megan ['attribute4', 'attribute5']
Harry ['attribute6', 'attribute7', 'attribute8']

现在所有的任务就是将它写入文件并检查案例,而不是每个人都有一组属性。

【讨论】:

  • 这还不完整,他还有其他顾虑。这显然值得一票......你不会从我这里得到的。
  • @Maresh 写最少的代码很容易,但我们不应该尝试帮助他解决问题而不是代替他解决问题吗?
  • 我同意。试过了。投了反对票...你会支持吗;-)
【解决方案3】:

这个怎么样:

with open("Names.txt") as namefile, open("Attributes.txt") as attfile:
    names = namefile.read().split("\n") 
    attributes = attfile.read().split("\n$$$$\n")

pairs = list(zip(names, attributes)) 

现在,每一对都将一个名称与相应位置的属性相关联,您可以进一步处理它以任意格式化。

【讨论】:

    猜你喜欢
    • 2012-04-22
    • 2020-07-05
    • 1970-01-01
    • 2016-05-05
    • 2017-04-28
    • 2013-08-24
    • 1970-01-01
    • 1970-01-01
    • 2014-12-13
    相关资源
    最近更新 更多