2017-02-14 62 views
0

所以我有这个从我的数据库返回的元组,这表明用户每天总共登录多少次。Python - Tuple分组字典

mytuple = 
(
    ('jim', datetime.date(2017, 2, 10), 1L), 
    ('jeff', datetime.date(2017, 2, 11), 1L), 
    ('jeff', datetime.date(2017, 2, 12), 1L), 
    ('jeff', datetime.date(2017, 2, 13), 1L), 
    ('jeff', datetime.date(2017, 2, 14), 26L) 
) 

如何以这种方式将它格式化为Dict/Json?

mydict = { 
    { 
     name: 'jeff', 
     data: [ 
      [(2017, 2, 11), 1], 
      [(2017, 2, 12), 1], 
      [(2017, 2, 13), 1], 
      [(2017, 2, 14), 26] 
     ] 
    }, 
    { 
     name: 'jim', 
     data: [ 
      [(2017, 2, 10), 1] 
     ] 
    } 
    } 

回答

0
import datetime 
import json 

mytype = (
    ('jim', datetime.date(2017, 2, 10), 1L), 
    ('jeff', datetime.date(2017, 2, 11), 1L), 
    ('jeff', datetime.date(2017, 2, 12), 1L), 
    ('jeff', datetime.date(2017, 2, 13), 1L), 
    ('jeff', datetime.date(2017, 2, 14), 26L) 
) 

mydict = {} 

for name, date, count in mytype: 
    if name not in mydict: 
     mydict[name] = [] 
    mydict[name].append(((date.year, date.month, date.day), count)) 

print mydict 
print json.dumps(mydict) 
+0

这并没有得到想要的格式 - 注意'name:'jeff'' – asongtoruin

+0

@ason​​gtoruin我知道它不是所需的格式,但是你说的'jeff'是什么? –

+0

问题要求以'name'作为关键字的字典,您提供了一个用户名作为关键字(而不是值) – asongtoruin

0

您可以使用下列内容:

import datetime 
import json 

mytype = (
    ('jim', datetime.date(2017, 2, 10), 1L), 
    ('jeff', datetime.date(2017, 2, 11), 1L), 
    ('jeff', datetime.date(2017, 2, 12), 1L), 
    ('jeff', datetime.date(2017, 2, 13), 1L), 
    ('jeff', datetime.date(2017, 2, 14), 26L) 
) 

output = [] 

def date_to_ymd_tuple(input_date): 
    return (input_date.year, input_date.month, input_date.day) 

for user in set(item[0] for item in mytype): 
    output.append({'name': user, 
        'data': [[date_to_ymd_tuple(x[1]), x[2]] for x in mytype if x[0] == user] 
        }) 

print output 

with open('output.txt', 'w') as f: 
    json.dump(output, f) 

将写出

[{"data": [[[2017, 2, 10], 1]], "name": "jim"}, {"data": [[[2017, 2, 11], 1], [[2017, 2, 12], 1], [[2017, 2, 13], 1], [[2017, 2, 14], 26]], "name": "jeff"}] 
1

您还可以使用itertools库,它有groupby功能做到这一点。希望这会更快,一旦你有更大的数据集。但是,输出将是列表而不是字典,与您所要求的不完全相同。

import datetime 
from itertools import groupby 

mytuple = [('jim', datetime.date(2017, 2, 10), 1), 
    ('jeff', datetime.date(2017, 2, 11), 1), 
    ('jeff', datetime.date(2017, 2, 12), 1), 
    ('jeff', datetime.date(2017, 2, 13), 1), 
    ('jeff', datetime.date(2017, 2, 14), 26)] 

group_dict = [] 
for key, group in groupby(mytuple, lambda x: x[0]): 
    group_dict.append({'name': key, 'data': [[g[1], g[2]] for g in group]}) 

这里你做groupby,并使用元组的第一个键为它提供函数,例如,这里lambda x: x[0]。在这种情况下,数据是各组指标1和2

您也可以使用元组的格式变换日期时间的因素太多,像以下:

group_dict = [] 
for key, group in groupby(mytuple, lambda x: x[0]): 
    data = [[(g[1].year, g[1].month, g[1].day), g[2]] for g in group] 
    group_dict.append({'name': key, 'data': data}) 
+0

没有想过使用'itertools' - 很好! – asongtoruin

+0

谢谢@ason​​gtoruin!只是你的答案:) – titipata

+0

伟大的工作@ason​​gtoruin @titipat!我对你的两个代码做了测试,看看它们的速度有多快,它们在单次运行中表现的速度一样快,并且很难获得准确的读数,但是它们都运行超过10,000次,@titipats的平均值为0.181068181992秒,并且@ason​​gtoruin超过了10秒,最有可能是因为'open('output.txt','w')作为f:':)谢谢你们的帮助!梦幻般的作品 – Slopax