遍历字典并修改值

Iterate through a dictionary and modify values

我试图通过递归遍历它的键来将字典中的特定日期时间值更改为字符串。

from copy import deepcopy
def datetoStr2(datadict):
if 'dict' in str(type(datadict)):
    newdict = dict()
    newdict.update(datadict)
    for key in datadict:
        if isinstance(datadict[key], dict):
            newdict[key] = datetoStr(datadict[key])
        if isinstance(datadict[key], list):
            mylist = datadict[key]
            for element in mylist:
                element = datetoStr(element)
        if isinstance(datadict[key], datetime):
        #newdict[key] = datadict[key].strftime('%Y-%m-%d %H:%M:%S.%f%z')
            newdict[key] = str(datadict[key])
    return newdict
else:
    return datadict

然而,当我运行

some_dict = datetoStr(mydict)

我在这些地方仍然有日期时间对象。我做错了什么?

编辑:更新了函数代码。

写这个函数是因为这个字典是通过 Flask 的 jsonify 传递的,它目前去除时区信息并将其替换为 GMT。 (计划在下一次更新中修复)。

我已经根据一些反馈更新了我的函数,但我仍然无法生成结果。

我正在添加一些示例数据和我的输出。

结果:

代码中插入的快速打印告诉我日期时间仍然是日期时间,并且 TZinfo 被 jsonify 剥离。

示例数据:

{'data': {'all': {'count': 2,
                  'data': [{'arrivalby': 'Wed, 20 Jun 2018 09:39:00 GMT',
                            'closesat': 'Wed, 20 Jun 2018 06:05:40 GMT',
                            'doctype': 'general',
                            'geofence': {'coordinates': [[[78.43786473803105,
                                                           17.447430456650043],
                                                          [78.45670406196896,
                                                           17.447430456650043],
                                                          [78.45670406196896,
                                                           17.46540214334996],
                                                          [78.43786473803105,
                                                           17.46540214334996],
                                                          [78.43786473803105,
                                                           17.447430456650043]]],
                                         'type': 'Polygon'},
                            'housecallid': '591ce42e9b53f96ea393934f61fab25d',
                            'lastupdated': 'Fri, 22 Jun 2018 04:32:14 GMT',
                            'requester': {'addr1': 'xxx xxx xx',
                                          'addr2': 'xx xx xx',
                                          'addr3': 'xx xx',
                                          'addrstate': 'xx',
                                          'city': 'xx',
                                          'dob': 'xx/xx/xxxx',
                                          'email': 'xx@xx',
                                          'fname': 'xxx',
                                          'lname': 'xx',
                                          'location': {'coordinates': [78.4472844,
                                                                       17.4564163],
                                                       'type': 'Point'},
                                          'mobile': xxxx,
                                          'sex': 'xxxx'},
                            'requesttime': 'Wed, 20 Jun 2018 00:05:40 GMT',
                            'responder': {'addr1': 'xxx xxxx',
                                          'addr2': 'xx xx xxxx',
                                          'addr3': 'xxx xx',
                                          'addrstate': 'xxxx',
                                          'city': 'xxxx',
                                          'email': 'xx@xxxx',
                                          'fname': 'xxxx',
                                          'lname': 'xxxx',
                                          'location': {'coordinates': [78.4471904,
                                                                       17.456458],
                                                       'type': 'Point'},
                                          'mobile': xxxx,
                                          'sex': 'xxxx'},
                            'responsetime': 'Wed, 20 Jun 2018 00:09:37 GMT',
                            'status': 'missed'},
                           {'arrivalby': 'Sat, 23 Jun 2018 10:13:00 GMT',
                            'closesat': 'Fri, 22 Jun 2018 10:42:11 GMT',
                            'doctype': 'general',
                            'geofence': {'coordinates': [[[78.43784273760974,
                                                           17.44743855664762],
                                                          [78.45668206239024,
                                                           17.44743855664762],
                                                          [78.45668206239024,
                                                           17.465410243352377],
                                                          [78.43784273760974,
                                                           17.465410243352377],
                                                          [78.43784273760974,
                                                           17.44743855664762]]],
                                         'type': 'Polygon'},
                            'housecallid': '998987171790f172b97a7981a8902af1',
                            'lastupdated': 'Fri, 22 Jun 2018 18:36:50 GMT',
                            'requester': {'addr1': 'xx xxx, ',
                                          'addr2': 'xx xx xxxx',
                                          'addr3': 'xxx xxx',
                                          'addrstate': 'xx',
                                          'city': 'xxxx',
                                          'dob': 'xxxx-xx-xx',
                                          'email': 'xxxx@xxxx',
                                          'fname': 'xx',
                                          'lname': 'xx',
                                          'location': {'coordinates': [78.4472624,
                                                                       17.4564244],
                                                       'type': 'Point'},
                                          'mobile': xxxx,
                                          'sex': 'xxxx'},
                            'requesttime': 'Fri, 22 Jun 2018 04:42:11 GMT',
                            'responder': {'addr1': 'xxxx xxxx',
                                          'addr2': 'xx xx xx',
                                          'addr3': 'xxxx xxxx',
                                          'addrstate': 'xxxx',
                                          'city': 'xxxx',
                                          'email': 'xxx@xxxx',
                                          'fname': 'xxxxx',
                                          'lname': 'xxxx',
                                          'location': {'coordinates': [78.4471904,
                                                                       17.456458],
                                                       'type': 'Point'},
                                          'mobile': xxxx,
                                          'sex': 'xx'},
                            'responsetime': 'Fri, 22 Jun 2018 04:43:05 GMT',
                            'status': 'missed'}]},
          'cancelled': {'count': 0, 'data': []},
          'closed': {'count': 0, 'data': []},
          'confirmed': {'count': 0, 'data': []},
          'missed': {'count': 2,
                     'data': [{'arrivalby': 'Wed, 20 Jun 2018 09:39:00 GMT',
                               'closesat': 'Wed, 20 Jun 2018 06:05:40 GMT',
                               'doctype': 'general',
                               'geofence': {'coordinates': [[[78.43786473803105,
                                                              17.447430456650043],
                                                             [78.45670406196896,
                                                              17.447430456650043],
                                                             [78.45670406196896,
                                                              17.46540214334996],
                                                             [78.43786473803105,
                                                              17.46540214334996],
                                                             [78.43786473803105,
                                                              17.447430456650043]]],
                                            'type': 'Polygon'},
                               'housecallid': '591ce42e9b53f96ea393934f61fab25d',
                               'lastupdated': 'Fri, 22 Jun 2018 04:32:14 GMT',
                               'requester': {'addr1': 'xx xx xxx',
                                             'addr2': 'xx xx xxxx',
                                             'addr3': 'xx xx',
                                             'addrstate': 'xxxxxx',
                                             'city': 'xxxxx',
                                             'dob': 'xx/xx/xxxx',
                                             'email': 'xx@xxx',
                                             'fname': 'xx',
                                             'lname': 'xxx',
                                             'location': {'coordinates': [78.4472844,
                                                                          17.4564163],
                                                          'type': 'Point'},
                                             'mobile': xx,
                                             'sex': 'xx'},
                               'requesttime': 'Wed, 20 Jun 2018 00:05:40 GMT',
                               'responder': {'addr1': 'xx xx',
                                             'addr2': 'xx xx xxxx',
                                             'addr3': 'xx xx',
                                             'addrstate': 'xx',
                                             'city': 'xx',
                                             'email': 'xx@xx',
                                             'fname': 'xx',
                                             'lname': 'xx',
                                             'location': {'coordinates': [78.4471904,
                                                                          17.456458],
                                                          'type': 'Point'},
                                             'mobile': xxxx,
                                             'sex': 'xx'},
                               'responsetime': 'Wed, 20 Jun 2018 00:09:37 GMT',
                               'status': 'missed'},
                              {'arrivalby': 'Sat, 23 Jun 2018 10:13:00 GMT',
                               'closesat': 'Fri, 22 Jun 2018 10:42:11 GMT',
                               'doctype': 'general',
                               'geofence': {'coordinates': [[[78.43784273760974,
                                                              17.44743855664762],
                                                             [78.45668206239024,
                                                              17.44743855664762],
                                                             [78.45668206239024,
                                                              17.465410243352377],
                                                             [78.43784273760974,
                                                              17.465410243352377],
                                                             [78.43784273760974,
                                                              17.44743855664762]]],
                                            'type': 'Polygon'},
                               'housecallid': '998987171790f172b97a7981a8902af1',
                               'lastupdated': 'Fri, 22 Jun 2018 18:36:50 GMT',
                               'requester': {'addr1': 'xxx xxx, ',
                                             'addr2': 'xx xx xxxx',
                                             'addr3': 'xx xx',
                                             'addrstate': 'xxx',
                                             'city': 'xxx',
                                             'dob': 'xxxx-xx-xx',
                                             'email': 'xxxx@xxxx',
                                             'fname': 'xx',
                                             'lname': 'xx',
                                             'location': {'coordinates': [78.4472624,
                                                                          17.4564244],
                                                          'type': 'Point'},
                                             'mobile': xxxxx,
                                             'sex': 'xx'},
                               'requesttime': 'Fri, 22 Jun 2018 04:42:11 GMT',
                               'responder': {'addr1': 'xx xx',
                                             'addr2': 'xx xx xxxx',
                                             'addr3': 'xx xx',
                                             'addrstate': 'xx',
                                             'city': 'xxxx',
                                             'email': 'xxxx@xxxx',
                                             'fname': 'xx',
                                             'lname': 'xx',
                                             'location': {'coordinates': [78.4471904,
                                                                          17.456458],
                                                          'type': 'Point'},
                                             'mobile': xx,
                                             'sex': 'xxxx'},
                               'responsetime': 'Fri, 22 Jun 2018 04:43:05 GMT',
                               'status': 'missed'}]}},  'success': True}

更新 - 2018 年 6 月 24 日

帕特里克,谢谢你的回答。我已经接受它是正确的。

但是,在我的编辑中,我谈到了列表是一个元素的想法,因此我添加了以下代码(对于那些正在寻找绕过 jsonify 错误的方法的人)。

def datetoStr(datadict):
    from copy import deepcopy
    # deepcopy before data manipulation
    if 'dict' in str(type(datadict)):
        newdict = deepcopy(datadict)

        for key,value in datadict.items():
            # recurse into nested dicts
            if isinstance(value, dict):
                newdict[key] = datetoStr(datadict[key])
            # convert to string
            elif isinstance(value, datetime):
                newdict[key] = str(datadict[key])
            # if list, iterate through elements and replace
            elif isinstance(datadict[key], list):
                newlist = datadict[key].copy()
                counter = 0
                for element in datadict[key]:
                    newlist[counter] = datetoStr(datadict[key][counter])
                    counter += 1
                newdict[key] = newlist
        return newdict
    else:
        return datadict

如果您使用 dict.items(),您可以稍微简化您的代码,它直接为您提供用于迭代的键和值:

from copy import deepcopy
import datetime 

def datetoStr(datadict):
    # deepcopy before data manipulation
    newdict = deepcopy(datadict)

    for key,value in datadict.items():
        # recurse into nested dicts
        if isinstance(value, dict):
            newdict[key] = datetoStr(datadict[key])
        # convert to string
        elif isinstance(value, datetime.datetime): 
            newdict[key] = str(datadict[key])

    return newdict


before = { "a date": datetime.datetime.now(),
           "a dict": { "another": datetime.datetime.now() + datetime.timedelta(hours=2)}}

print(before)

# get the modified copy of before
transformedDict = datetoStr(before) 
print(transformedDict)

输出:

# before        
{'a date': datetime.datetime(2018, 6, 23, 21, 54, 12, 806419), 
 'a dict': {'another': datetime.datetime(2018, 6, 23, 23, 54, 12, 806421)}}

# transformedDict
{'a date': '2018-06-23 21:54:12.806419', 
 'a dict': {'another': '2018-06-23 23:54:12.806421'}}