首页 > 解决方案 > 合并 2 个文件以创建 1 个文件作为输出

问题描述

我得到了 2 个文件,如下所示: 首先:

port2
port4
port10
etc.

第二:

port1
some stuff
about the port
I do not need
!
port2
some stuff
about the port
I really need
!
some generic stuff which is completely useless
!
port3
some stuff
about the port
I do not need
!
port4
some stuff
about the port
I really need
!
etc

现在,我想要创建一个循环,对于第一个文档中的每一行,我们将遍历第二个文档并创建一个包含我需要的所有数据的新文件(“port2”直到“!”,“port4”直到“!”等)

到目前为止我得到了什么:

def access():
with open ("D:/portlist.txt") as f1, open ("D:/config.txt") as f2:
    match = False
    for line in f1:
        newConfig = open ("D:/portconfig.test.txt", "a")
        interface = line
        for line2 in f2:
            if re.match(interface, line2):
                newConfig.write(line2)
                print(line2)
                match = True
            elif re.match("!", line2):
                match = False   
            elif match:
                newConfig.write(line2)
        newConfig.close()   
access()

问题是脚本在返回所有关于 port2 后停止。脚本似乎没有返回到第一个循环以继续该过程。有任何想法吗?

标签: pythonloopsfor-loopif-statement

解决方案


您的问题源于这样一个事实,即一旦文件被读取到最后,它不会自动返回到第一点。由于您要为搜索的每个值循环遍历第二个文件,因此您要么需要通过 回溯f2.seek(0),要么只需在内存中读取文件的内容一次,然后循环。

关于您的代码,一个快速(且肮脏)的解决方案利用了您有块分隔符()的事实!

with open(...) as f1, open(...) as f2:
  section_names_to_keep = f1.read().splitlines()
  config_content = f2.read()

config_blocks = config_content.split('!\n')
blocks_to_keep = [ bl for bl in config_blocks if bl.splitlines()[0] in section_names_t_keep ]

with open('your_output_file.txt', 'a') as fp:
  fp.write('!\n'.join(blocks_to_keep))

注意:您对预期的输出格式不太清楚,所以我认为它应该看起来像config.txt. 我一次写入输出文件(首先我在内存中生成输出内容,'!\n'.join(blocks_to_keep)然后将其写出)。如果(正如我假设的那样)您的数据很小,这将不是问题。如果不是这种情况,只需循环blocks_to_keep并逐块写出。

小代码说明:

在第一个块中,我只是加载两个文件的内容。因为对于第一个文件,我们对每一行都感兴趣,所以我已经将它分成了几行。

在第二个块中,我在块分隔符上拆分配置!\n,然后过滤块列表,仅保留第一行在我们从第一个文件获得的列表中的那些块。

第三块只是输出。


推荐阅读