【问题标题】:Python text file into .csvPython 文本文件转换为 .csv
【发布时间】:2014-01-21 10:00:10
【问题描述】:

首先,感谢您阅读我的帖子。从 .txt 文件解析数据并将其放入 .csv 文件时,我遇到了一个特殊问题。从文本文档中,我尝试从路由器配置文件中绘制主机名和环回地址,然后将其放在 Excel 表中的单独列中。相反,当我添加“outFile.write(”“.join(buffer))”时,它在 excel 表中变得一团糟,它还添加了打印函数没有的字符串。

代码如下:

inFile = open("Data.txt")
outFile = open("result.csv", "w")
buffer = []
keepCurrentSet = True
for line in inFile:
        buffer.append(line)
        if line.startswith ("hostname"):
                print (line) 
                outFile.write("".join(buffer))
        elif line.startswith("interface Loopback"):
                print (line)
                print (next(inFile))
                outFile.write("".join(buffer))
inFile.close()
outFile.close()

这是文本文件

[spoiler]
version 12.4
service timestamps debug datetime msec
service timestamps log datetime msec
no service password-encryption
!
hostname cisco1841
!
boot-start-marker
boot-end-marker
!
logging buffered 51200 warnings
!
no aaa new-model
clock timezone Arizona -7
ip cef
!
!
no ip dhcp use vrf connected
!
ip dhcp excluded-address 10.10.1.1
ip dhcp excluded-address 10.10.3.1
!
ip dhcp pool Inside
network 10.10.1.0 255.255.255.0
dns-server 205.171.3.65 4.2.2.1
default-router 10.10.1.1
!
ip dhcp pool Wireless
import all
network 10.10.3.0 255.255.255.0
dns-server 205.171.3.65 4.2.2.1
default-router 10.10.3.1
lease 3
!
!
multilink bundle-name authenticated
!
!
!
!
username xxxxxxx privilege 15 secret 5 xxxxxxxxxx
!
bridge irb
!
!
!
interface Loopback0
ip address 10.10.0.1 255.255.255.255
!
interface FastEthernet0/0
description Inside LAN
ip address 10.10.1.1 255.255.255.0
ip nat inside
duplex auto
speed auto
[/spoiler]

【问题讨论】:

  • 请详细说明您希望输出是什么样的确切!究竟是什么问题?根据您的问题,您的脚本似乎可以工作,但我们无法确定预期的输出!

标签: python python-3.x


【解决方案1】:

如果您尝试在 excel 中打开 .csv,它的可读性可能不会很高。 csv 代表逗号分隔值,您的输出没有逗号,但有很多空格和换行符 - 真的不能指望 excel 来处理这些。以下是程序的输出(加上换行符):

hostname cisco1841

interface Loopback0

ip address 10.10.0.1 255.255.255.255

您可以通过在输出文件中添加逗号来代替已经存在的空格来更正确地格式化输出。对于您要抓取的 ip 地址行,它更难,因为它的名称中也有空格。我通过抓住该行中列出的第一个 ipAddress 解决了这个问题——如果你想要另一个或两个,这很容易解决。我还删除了您正在使用的缓冲区和“keepCurrentResultSet”,因为我确实不需要它们。

inFile = open("text.txt")
outFile = open("result.csv", "w")
for line in inFile:
        if line.startswith ("hostname"):
                outFile.write(line.replace(' ',','))
        elif line.startswith("interface Loopback"):
                outFile.write(line.replace(' ',','))
                ipAddrLine = next(inFile)
                ipAddress = ipAddrLine.split(' ')[2:3]
                outFile.write('ip address,' + ','.join(ipAddress))
inFile.close()
outFile.close()

这给出了这个输出,它应该被 excel 认为是有效的 .csv 格式:

hostname,cisco1841
interface,Loopback0
ip address,10.10.0.1

【讨论】:

    【解决方案2】:
    buffer = []
    

    buffer 是一个列表。对于您附加到原始文件中的每一行:

    for line in inFile:
        buffer.append(line)
    

    因此它将始终包含已读取的所有行的列表。

    outFile.write("".join(buffer))
    

    然后,每次找到相关行时,您都将整个 buffer 写入文件。但是因为buffer 是所有读取行的列表,所以您基本上重复地将所有先前读取的行的串联写入文件中。

    您应该改为写以下行:

    outFile.write(line)
    

    您无需在此处推进文件迭代器:print (next(inFile))。 for 循环已经在这样做了。

    如果您进行这些更改,脚本将过滤以"hostname""interface Loopback" 开头的行。 buffer 根本不需要。如果您确实想要"interface Loopback" 之后的行,那么您应该替换

    print (next(inFile))
    

    line = next(inFile)
    

    但这似乎不是你想要的。不过我真的不知道你想做什么。

    所以我的猜测是您希望将主机名和 IP 地址放入两列,然后可能会遍历许多文件。在这种情况下,您可以读取整个文件(假设它不太长)并使用正则表达式来过滤您需要的内容。然后你可以在csv的帮助下写出结果:

    import csv
    import re
    
    outFile = open("result.csv", "w")
    outFileCsv = csv.writer(outFile)
    outFileCsv.writerow(["hostname", "loopback ip"])
    
    for filename in ["Data.txt"]: # Add more files here
        try:
            inFile = open(filename).read()
        except IOError:
            print("Could not read {0}".format(filename))
            continue
        try:
            hostname = re.search("\nhostname (.*)\n", inFile).group(1)
            loopback_ip = re.search("\ninterface Loopback.*\n(?!\ninterface).*ip address ([0-9\\.]*)", inFile).group(1)
        except AttributeError:
            print("No match in {0}".format(filename))
            continue    
        outFileCsv.writerow([hostname, loopback_ip])
    
    outFile.close()
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2023-03-20
      • 1970-01-01
      • 2018-07-22
      • 1970-01-01
      • 1970-01-01
      • 2017-11-05
      • 2019-04-28
      • 2021-03-11
      相关资源
      最近更新 更多