【问题标题】:python dictionary with list of tuples to CSV带有元组列表的python字典到CSV
【发布时间】:2017-09-11 03:15:27
【问题描述】:

怎么会有这样的python字典:

{
    'RCLS1': [(0, 20),  (10, 112),  (20, 130), (30, 102)],
    'RCLS2': [(0, 16),(10, 53),(20, 96), (30, 45)]
}

转换为具有结构的 CSV:

RCLS1,  0,  20
RCLS1, 10, 112
.
.
.
RLCS2, 30,  45

我试过这个:

with open(r'E:\data.csv', "wb") as f:
    csv.writer(f).writerows((k,) + v for k, v in dct.items())

但这导致了以下错误:

can only concatenate tuple (not "list") to tuple

【问题讨论】:

  • 您希望输出是什么样的。目前v 是一个元组列表,因此(k,) + v 正在尝试将tuple 添加到它无法执行的元组列表中。
  • @AChampion 同意了。你能提供一个预期输出的例子吗?
  • 感谢您的 cmets。同意,我对预期输出的解释写得不好。现在已经包含了一个示例。

标签: python csv dictionary


【解决方案1】:

根据您提供的示例输入/输出,您可以遍历字典的键值对,然后遍历与每个键关联的元组值列表,构建关联的 CSV 行字符串,并将其写入 CSV文件,像这样:

dct = {'RCLS1':[(0, 20),  (10, 112),  (20, 130), (30, 102)], 'RCLS2': [(0, 16),(10, 53),(20, 96), (30, 45)]}
int_to_str = lambda int_value: str(int_value)

with open(r"data.csv", "w") as csv_file:
    for key, values in dct.items():
         for tuple_value in values:
             csv_row = [key] + list(map(int_to_str, list(tuple_value)))
             csv_file.write(", ".join(csv_row) + "\n")

data.csv 结果:

RCLS2, 0, 16
RCLS2, 10, 53
RCLS2, 20, 96
RCLS2, 30, 45
RCLS1, 0, 20
RCLS1, 10, 112
RCLS1, 20, 130
RCLS1, 30, 102

【讨论】:

  • 感谢您的想法。我已经编辑了问题以澄清输出。我之前还不够清楚。我很抱歉。如果可以,请再看一眼并分享您的想法。非常感谢。
  • @JacamoFinane 不客气。您可以尝试更新的答案吗?
  • 这看起来很棒,@Robert Valencia,感谢您向我展示了达到所需输出的有效方法。感谢您的指导。我学到了一些新东西。
  • 不客气@JacamoFinane!如果它帮助/解决了您的问题,请投票/接受答案。
  • @JacamoFinane 在 Python 3 中发生错误,因为 map 返回一个可迭代对象,因此返回的值应显式转换为列表。请查看更新后的答案,如果可行,请告诉我。
【解决方案2】:

如果我从你的问题中理解的是正确的,那么你正在尝试做这样的事情(不需要使用csv 模块):

a = {'RCLS1':[(0, 20),  (10, 112),  (20, 130), (30, 102)], 'RCLS2': [(0, 16),(10, 53),(20, 96), (30, 45)]}

with open('E:\data.csv', 'a+') as f:
    for k,v in a.items():
        f.write("{0}: {1}\n".format(k,", ".join(", ".join(str(j) for j in k) for k in v)))

输出(文件中的日期将与此输出类似):

RCLS1: 0, 20, 10, 112, 20, 130, 30, 102
RCLS2: 0, 16, 10, 53, 20, 96, 30, 45

否则,如果您想成对获取数据,您可以执行以下操作:

with open('E:\data.csv', 'a+') as f:
    for k,v in a.items():
        f.write("{0}: {1}\n".format(k, "".join(", ".join(str(k) for k in v))))

输出:

RCLS1: (0, 20), (10, 112), (20, 130), (30, 102)
RCLS2: (0, 16), (10, 53), (20, 96), (30, 45)

编辑:

新更新的快速解决方案。你可以这样做:

a = {'RCLS1':[(0, 20),  (10, 112),  (20, 130), (30, 102)], 'RCLS2': [(0, 16),(10, 53),(20, 96), (30, 45)]}

with open('E:\data.csv', 'a+') as f:
    for k,v in a.items():
        for j in v:
            f.write("{0}: {1}\n".format(k, ", ".join(str(k) for k in j)))

输出:

RCLS2: 0, 16
RCLS2: 10, 53
RCLS2: 20, 96
RCLS2: 30, 45
RCLS1: 0, 20
RCLS1: 10, 112
RCLS1: 20, 130
RCLS1: 30, 102

【讨论】:

  • 非常感谢您的想法。看了我原来的描述,我理解你的建议。您介意看一下我提供的输出格式示例(编辑问题后)吗?谢谢。
  • 谢谢@ChihebNexus,您建议的最后一种方法符合我的目标。感谢您的所有建议。学到了新东西!
【解决方案3】:

使用pandas 的另一种答案:

>>> import pandas as pd
>>> d={'RCLS1':[(0, 20),  (10, 112),  (20, 130), (30, 102)], 'RCLS2': [(0, 16),(10, 53),(20, 96), (30, 45)]}
>>> df=pd.DataFrame(d)


       RCLS1     RCLS2
0    (0, 20)   (0, 16)
1  (10, 112)  (10, 53)
2  (20, 130)  (20, 96)
3  (30, 102)  (30, 45)
[4 rows x 2 columns]

>>> dfs=df.stack().reset_index(level=0)

       level_0          0
RCLS1        0    (0, 20)
RCLS2        0    (0, 16)
RCLS1        1  (10, 112)
RCLS2        1   (10, 53)
RCLS1        2  (20, 130)
RCLS2        2   (20, 96)
RCLS1        3  (30, 102)
RCLS2        3   (30, 45)


>>> dfs=dfs[0].apply(pd.Series)  # break the tuples in column with "name"=0

        0    1
RCLS1   0   20
RCLS2   0   16
RCLS1  10  112
RCLS2  10   53
RCLS1  20  130
RCLS2  20   96
RCLS1  30  102
RCLS2  30   45


>>> dfs.to_csv('fileName.csv')

【讨论】:

  • 谢谢你,@ab-user216125,这也太完美了,b/c 我希望能更精通给同一只猫剥皮的几种方法。这将被添加到武器库中!谢谢
  • 我正在使用各种解决方案,@ab-user216125。不幸的是,我的数千个项目的字典包含一些长度与其他值不同的值,因此在调用 df=pd.DataFrame(d) 时,会出现错误“数组必须都是相同长度”的结果。我很好奇 pandas DF 在这种情况下是否仍然是一个选项?
  • 如果您的 RCLS1 和 RCLS2 或 RCLSn 的长度发生变化,您最终可能会得到稀疏的 DataFrame。在这种情况下,您需要考虑您的数据是否如您所想。 Pandas 可以很好地处理缺失数据或删除行/列或填充缺失值。你将如何处理这些事情完全取决于你。如果您喜欢答案,请投票 - 每个人都喜欢赚取积分 ;)
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2021-04-26
  • 1970-01-01
  • 2021-04-02
  • 1970-01-01
  • 2016-04-19
  • 2016-03-19
  • 2015-12-21
相关资源
最近更新 更多