【问题标题】:From text file to dictionary从文本文件到字典
【发布时间】:2016-04-15 15:04:11
【问题描述】:

我是一个 txt 文件,并获取字符串并将第一个作为我正在创建的字典的键,其余的将是我作为元组的值。手头有标题,我已经让我的代码在开始时“忽略”它。

txt 值示例:

"Ronald Reagan","1981","8","69","California","Republican"
"George Bush","1989","4","64","Texas","Republican"
"Bill Clinton","1993","8","46","Arkansas","Democrat"

我想创建提供以下输出的字典:

{"Ronald Reagan": (1981,8,69,"California", "Republican") etc.}

这是我目前拥有的代码:

def read_file(filename):
    d={}
    f= open(filename,"r")
    first_line = f.readline()
    for line in f:
        #line=line.strip('"')
        #line=line.rstrip()
        data=line.split('"')
        data=line.replace('"', "")

        print(data)


        key_data=data[0]

        values_data= data[1:]
        valuesindata=tuple(values_data)
        d[key_data]=valuesindata

    print(d)

read_file(filename)

第一个打印语句(我把它放在那里只是为了看看当时的输出是什么,它给了我以下信息:

Ronald Reagan,1981,8,69,California,Republican
George Bush,1989,4,64,Texas,Republican

等等。当它到达第二个打印语句时,它会执行以下操作:

{'R': ('o', 'n', 'a', 'l', 'd', ' ', 'R', 'e', 'a', 'g', 'a', 'n', ',', '1', '9', '8', '1', ',', '8', ',', '6', '9', ',', 'C', 'a', 'l', 'i', 'f', 'o', 'r', 'n', 'i', 'a', ',', 'R', 'e', 'p', 'u', 'b', 'l', 'i', 'c', 'a', 'n', '\n'), 'G': ('e', 'o', 'r', 'g', 'e', ' ', 'B', 'u', 's', 'h', ',', '1', '9', '8', '9', ',', '4', ',', '6', '4', ',', 'T', 'e', 'x', 'a', 's', ',', 'R', 'e', 'p', 'u', 'b', 'l', 'i', 'c', 'a', 'n', '\n')}

另外,我将其拆分为引号,因为我的某些字符串包含逗号作为名称的一部分,例如:“Carl, Jr.”

我不想导入 csv 模块,有没有办法做到这一点?

【问题讨论】:

  • 是的,但是我是有限的,不能导入任何模块作为限制。

标签: python csv dictionary


【解决方案1】:

您可以像 alecxe 建议的那样使用 csv 模块,也可以像这样“手动”执行此操作:

csv_dict = {}

with open(csv_file, 'r') as f:
    for line in f:
        line = line.strip().replace('"', '').split(',')
        csv_dict[line[0]] = tuple(int(x) if x.isdigit() else str(x) for x in line[1:])

这将删除双引号,将数值转换为 int 并创建一个元组字典。

【讨论】:

  • 这适用于名称中没有逗号的名称。所以它适用于像“Ronald Reagan”这样的名字,但不适用于像“Ronald Reagan, Jr.”这样的名字。 ,因为它会将名字拆分为“Ronald Reagan”“Jr.”
  • @Nick True,为此您需要 csv 模块或更复杂的手动处理行;即检查引号内的逗号并以不同方式处理这些边缘情况
  • 你帮了大忙,我只是迷失了如何去做,否则没有分开逗号包含在名称中的位置。
  • @Nick 谢谢,不客气。我也不知道还能做什么......我刚刚制作了一个无需导入即可工作的版本,但它并不漂亮。我通过用分隔符元组中的替代分隔符替换所有没有被引号包围的逗号(逗号两边的引号表示它是分隔符)来做到这一点 - 但只有在确保新分隔符不存在之后文本。然后是用逗号替换新的分隔符被逗号分割......等等瞧“Ronald Reagan, Jr.”。 :P
【解决方案2】:

导致这个奇怪结果的代码中的主要问题是 data 变量是一个字符串,data[0] 会给你第一个字符,data[1:] 其余的 - 你需要调用 split(",") 来第一次拆分将字符串放入列表中。

我有一个限制,不能导入任何模块。

这个想法是使用split(",") 将每行拆分为单独的项目,并使用strip() 删除项目值周围的引号:

d = {}
with open(filename) as f:
    for line in f:
        items = [item.strip('"').strip() for item in line.split(",")]
        d[items[0]] = items[1:]

print(d)

打印:

{'Bill Clinton': ['1993', '8', '46', 'Arkansas', 'Democrat'],
 'George Bush': ['1989', '4', '64', 'Texas', 'Republican'],
 'Ronald Reagan': ['1981', '8', '69', 'California', 'Republican']}

仅供参考,使用标准库中的csv module 会使事情变得更容易:

import csv
from pprint import pprint

d = {}
with open(filename) as f:
    reader = csv.reader(f)
    for row in reader:
        d[row[0]] = row[1:]

pprint(d)

你也可以使用字典理解

d = {row[0]: row[1:] for row in reader}

【讨论】:

  • 是的,我同意这会让生活变得更轻松,但我有一个限制,不能导入任何模块。
猜你喜欢
  • 1970-01-01
  • 2021-11-25
  • 2018-01-11
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-04-10
  • 2013-03-15
相关资源
最近更新 更多