将3个列表解析为python中的字典列表

Posted

技术标签:

【中文标题】将3个列表解析为python中的字典列表【英文标题】:parsing 3 lists into list of dictionaries in python 【发布时间】:2021-12-30 23:01:31 【问题描述】:

我正在逐行解析 csv。一行中有 3 列需要将每列拆分为列表,然后在列表中组合成字典。每列内的数据由两个管道分隔:||

传入数据:

按钮,点击,id 选择1 ||选择2 ||选择 3,正确 ||错误 ||错误,选择 1 id||选择 2 id ||选择 3 id

数据已通过 csv DiskReader 导入,脚本中的每一行都是有序字典,如下所示:
('buttons','choice 1 || choice 2 || choice 3'),
('clicked', 'TRUE || FALSE || FALSE'),
('id','choice 1 id|| choice 2 id || choice 3 id'),

编辑添加: input 有很多不应该包含的列。此步骤仅包含这 3 列。

即正在处理的行的示例输出

print(data[0])

OrderedDict([
('pathId', 'test_id'),
('stepId', ''),
('nodeId', 'ROOT'),
('responseId', 'test_response'),
('responseUuid', ''),
('type', ''),
('language', 'en-US'),
('buttons','choice 1 || choice 2 || choice 3'),
('clicked', 'TRUE || FALSE || FALSE'),
('id','choice 1 id|| choice 2 id || choice 3 id'),
('state', 'resolved'),
('flags', 'accepted')])

实际的列数是动态的且不可预测的。但在包含 buttonsclickedid 值的行中将需要此处理。END EDIT

此行的

预期输出需要:

buttonChoices =
[
    
        "button": "choice 1",
        "clicked": true,
        "id": "choice 1 id"
    ,
    
        "button": "choice 2",
        "clicked": false,
        "id": "choice 2 id"
    ,
    
        "button": "choice 3",
        "clicked": false,
        "id": "choice 3 id"
    
]
我事先不知道列表中有多少个值,但是这 3 列中的值是相同的

现在我有:

for row in data:
    buttonChoices = []
    buttonText = row['button'].split('||')
    buttonClicked = row['clicked'].split('||')
    buttonId = row['id'].split('||')

但卡住了下一步

【问题讨论】:

为什么您的 CSV 看起来像这样?为什么每个按钮点击事件没有单独的一行数据? 就是这样...所有相关记录都排成一行 【参考方案1】:

您可以使用 zip 将值 3 x 3 组合并将它们与键相关联:

data = dict([ ('buttons','choice 1 || choice 2 || choice 3'),
              ('clicked', 'TRUE || FALSE || FALSE'),
              ('id','choice 1 id|| choice 2 id || choice 3 id')])

buttonChoices = [ dict(zip(data,map(str.strip,values)))
                  for values in zip(*(v.split("||") for v in data.values())) ]

print(buttonChoices)
['buttons': 'choice 1', 'clicked': 'TRUE', 'id': 'choice 1 id',
 'buttons': 'choice 2', 'clicked': 'FALSE', 'id': 'choice 2 id',
 'buttons': 'choice 3', 'clicked': 'FALSE', 'id': 'choice 3 id']

注意:我在其中添加了一个 map(str.strip,...) 来清理混乱的字符串分隔,但如果您的实际数据格式正确,则不需要它

为了概括这一点,您可以定义输入键和输出键以根据需要进行过滤和重命名:

inKeys  = ('buttons','clicked','id')
outKeys = ('button','clicked','id')
buttonChoices = [ dict(zip(outKeys,map(str.strip,values)))
                  for values in zip(*(data[k].split("||") for k in inKeys)) ]

print(buttonChoices)
['button': 'choice 1', 'clicked': 'TRUE', 'id': 'choice 1 id',
 'button': 'choice 2', 'clicked': 'FALSE', 'id': 'choice 2 id',
 'button': 'choice 3', 'clicked': 'FALSE', 'id': 'choice 3 id']

【讨论】:

我认为如果“数据”中没有其他字典值,这可行,但原始 csv 中有更多列不需要添加到此部分。 (他们得到单独的处理)有没有办法通过键限制data中的内容?像熊猫data['buttons', 'clicked', 'id] 这应该是可能的,但我需要查看源数据和预期排除的示例(在您的问题中,而不是在评论中)才能正确回答。 我在问题中添加了编辑 我明白了,我添加到答案中的“通用”版本应该涵盖了这一点。【参考方案2】:

如果我正确理解了这个问题,那么这应该可以工作。

    button_choices = []
    for row in data:
        button_texts = row['button'].split('||')
        button_clickeds = row['clicked'].split('||')
        button_ids = row['id'].split('||')
        for button_text, button_clicked, button_id in zip(button_texts, button_clickeds, button_ids):
            button_choices.append(
                'button': button_text,
                'clicked': button_clicked,
                'id': button_id
            )

【讨论】:

以上是关于将3个列表解析为python中的字典列表的主要内容,如果未能解决你的问题,请参考以下文章

python列表解析式,字典解析式,集合解析式和生成器

第4.4节 Python解析与推导:列表解析字典解析集合解析

第二天 Python3.4.2 里面的字典 列表解析等等

python 列表解析字典的两个小方法

Python生成器, 列表解析与字典解析

Python解析CSV中的多维字典