【问题标题】:How to convert a list of strings to list of dictionaries in python?如何将字符串列表转换为python中的字典列表?
【发布时间】:2017-04-10 21:36:18
【问题描述】:

我有一个格式为:

["('colA':'datA1', 'colB':'datB1', 'colC':'datC1')",
 "('colA':'datA2', 'colB':'datB2', 'colC':'datC2')",
 ..........
 "('colA':'datAn', 'colB':'datBn', 'colC':'datCn')]

我需要获取一个字典:

[{'colA': 'datA1', 'colB': 'datB1', 'colC': 'datC1'},
 {'colA': 'datA2', 'colB': 'datB2', 'colC': 'datC2'},
 ..........
 {'colA': 'datAn', 'colB': 'datBn', 'colC': 'datCn'}]

如果可能的话,我需要使用 Python 自己的函数,或者至少不使用循环,但我不知道这是否可行。

【问题讨论】:

  • “杰克”从何而来?这不在原始数据中。萨佩也不是。数字 4098 和 4130 是从哪里来的?来自计算?
  • 抱歉,剪贴板出错。感谢您指出。我编辑
  • 呵呵,如果不是字符串中的 ( 和 ),您可以在每个字符串上运行 eval()

标签: python string list dictionary


【解决方案1】:

用大括号替换括号并使用ast.literal_eval:

import ast
l = ["('colA':'datA1', 'colB':'datB1', 'colC':'datC1')",
 "('colA':'datA2', 'colB':'datB2', 'colC':'datC2')",
 "('colA':'datAn', 'colB':'datBn', 'colC':'datCn')"]
result = [ast.literal_eval('{%s}' % item[1:-1]) for item in l]

结果:

>>> import pprint
>>> pprint.pprint(result)
[{'colA': 'datA1', 'colB': 'datB1', 'colC': 'datC1'},
 {'colA': 'datA2', 'colB': 'datB2', 'colC': 'datC2'},
 {'colA': 'datAn', 'colB': 'datBn', 'colC': 'datCn'}]

【讨论】:

【解决方案2】:

正如@nexus66 所建议的,这是that answer 的更精简版本:

l = ["('colA':'datA1', 'colB':'datB1', 'colC':'datC1')",
 "('colA':'datA2', 'colB':'datB2', 'colC':'datC2')",
 "('colA':'datAn', 'colB':'datBn', 'colC':'datCn')"]
result = [dict(
               item.replace("'", '').split(':')
               for item in s[1:-1].split(', ')
               )
          for s in l]

【讨论】:

  • 感谢您的回答!
  • 谢谢你给我的两个答案。我更喜欢这个不使用额外的模块。
【解决方案3】:

避免使用eval(因为它不安全)函数并依赖正确的dict结构(在json表示中)。对re.subjson.loads 函数使用以下方法:

import json, re

d = ["('colA':'datA1', 'colB':'datB1', 'colC':'datC1')",
 "('colA':'datA2', 'colB':'datB2', 'colC':'datC2')",
 "('colA':'datAn', 'colB':'datBn', 'colC':'datCn')"]

try:
    l = [json.loads('{' + re.sub(r'\'', '"', s).strip('()') + '}') for s in d]
    print(l)
except json.decoder.JSONDecodeError as err:
    print('JSONDecodeError: ', err)

输出:

[{'colC': 'datC1', 'colA': 'datA1', 'colB': 'datB1'}, {'colC': 'datC2', 'colA': 'datA2', 'colB': 'datB2'}, {'colC': 'datCn', 'colA': 'datAn', 'colB': 'datBn'}]

【讨论】:

  • except: 应该捕获什么样的异常?
  • @TigerhawkT3,在一些简单的情况下它可以是bare,但现在我添加了特定的异常类型,请参阅我的更新。当然,在更严格(真实)的情况下,我们可以raise Exception('...')
【解决方案4】:

我在不导入任何模块的情况下解决您的问题:

my_input = ["('colA':'datA1', 'colB':'datB1', 'colC':'datC1')",
 "('colA':'datA2', 'colB':'datB2', 'colC':'datC2')",
 "('colA':'datAn', 'colB':'datBn', 'colC':'datCn')"]

global_list =[]
for i in my_input:
    intern_dict = {}
    for j in i.replace("(", "").replace(")", "").split(","):
        c = j.split(":")
        intern_dict["".join(c[0].replace("'", "").strip())] = "".join(c[1].replace("'","").strip())     
    global_list.append(intern_dict)

print("Type of global_list: {0}\n".format(type(global_list)))
print(global_list)
print("\nType of elements inside global_list\n")
for i in global_list:
    print("{0}\tType: {1}".format(i, type(i)))

输出:

Type of global_list: <class 'list'>

[{'colA': 'datA1', 'colC': 'datC1', 'colB': 'datB1'}, {'colA': 'datA2', 'colC': 'datC2', 'colB': 'datB2'}, {'colA': 'datAn', 'colC': 'datCn', 'colB': 'datBn'}]

Type of elements inside global_list

{'colA': 'datA1', 'colC': 'datC1', 'colB': 'datB1'} Type: <class 'dict'>
{'colA': 'datA2', 'colC': 'datC2', 'colB': 'datB2'} Type: <class 'dict'>
{'colA': 'datAn', 'colC': 'datCn', 'colB': 'datBn'} Type: <class 'dict'>

【讨论】:

  • 这个算法有一些明显的奇怪之处,比如k for k in...不必要的生成器表达式。
  • ''.join(k for k in iterable) 完成与''.join(iterable) 相同的结果。
  • 是的!你说得对。我编辑了我的答案。感谢您指出奇怪之处。
  • 整个事情可能只是result = [dict(item.replace("'", '').split(':') for item in s[1:-1].split(', ')) for s in my_input]
  • 太棒了!您应该发布您的解决方案。它更像是 Pythonic!
【解决方案5】:

使用json,

import json

lst = "yourstringhere"

dict = json.load(lst)

【讨论】:

    猜你喜欢
    • 2019-07-31
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多