20

我正在尝试dict使用以下方式将以下内容转换为 JSON json.dumps

 {
     'post_engaged': 36,
     'post_impressions': 491,
     'post_story': 23,
     'comment_count': 6,
     'created_time': '03:02 AM, Sep 30, 2012',
     'message': 'Specialities of Shaktis and Pandavas. \n While having power, why there isn\\u2019t',
     < built - in function id > : '471662059541196',
     'status_type': 'status',
     'likes_count': 22
 } {
     'post_engaged': 24,
     'text': '30 Sept 2012 Avyakt Murlli ( Dual Voice )',
     'post_story': 8,
     'comment_count': 3,
     'link': 'http:\\/\\/www.youtube.com\\/watch?v=VGmFj8g7JFA&feature=youtube_gdata_player',
     'post_impressions': 307,
     'created_time': '03:04 AM, Sep 30, 2012',
     'message': 'Not available',
     < built - in function id > : '529439300404155',
     'status_type': 'video',
     'likes_count': 7
 } {
     'post_engaged': 37,
     'post_impressions': 447,
     'post_story': 22,
     'comment_count': 4,
     'created_time': '03:11 AM, Sep 30, 2012',
     'message': '30-09-12 \\u092a\\u094d\\u0930\\u093e\\u0924:\\u092e\\u0941\\u0930\\u0932\\u0940 \\u0913\\u0',
     < built - in function id > : '471643246209744',
     'status_type': 'status',
     'likes_count': 20
 } {
     'post_engaged': 36,
     'post_impressions': 423,
     'post_story': 22,
     'comment_count': 0,
     'created_time': '03:04 AM, Sep 29, 2012',
     'message': 'Essence: Sweet children, whenever you have time, earn the true income. Staying i',
     < built - in function id > : '471274672913268',
     'status_type': 'status',
     'likes_count': 20
 } {
     'post_engaged': 16,
     'text': 'Essence Of Murli 29-09-2012',
     'post_story': 5,
     'comment_count': 2,
     'link': 'http:\\/\\/www.youtube.com\\/watch?v=i6OgmbRsJpg&feature=youtube_gdata_player',
     'post_impressions': 291,
     'created_time': '03:04 AM, Sep 29, 2012',
     'message': 'Not available',
     < built - in function id > : '213046588825668',
     'status_type': 'video',
     'likes_count': 5
 }

但它引导我

TypeError : keys must be a string

该错误可能是由于 dict 包含,keys例如:

 <built-in function id>: '213046588825668'

有人可以指导我,我应该如何从字典中删除这些元素?

4

7 回答 7

19

您可以尝试像这样清理它:

for key in mydict.keys():
  if type(key) is not str:
    try:
      mydict[str(key)] = mydict[key]
    except:
      try:
        mydict[repr(key)] = mydict[key]
      except:
        pass
    del mydict[key]

这将尝试将任何不是字符串的键转换为字符串。任何无法转换为字符串或表示为字符串的键都将被删除。

于 2012-10-04T19:38:12.610 回答
9

修改上面接受的答案,我写了一个函数来处理任意深度的字典:

def stringify_keys(d):
    """Convert a dict's keys to strings if they are not."""
    for key in d.keys():

        # check inner dict
        if isinstance(d[key], dict):
            value = stringify_keys(d[key])
        else:
            value = d[key]

        # convert nonstring to string if needed
        if not isinstance(key, str):
            try:
                d[str(key)] = value
            except Exception:
                try:
                    d[repr(key)] = value
                except Exception:
                    raise

            # delete old key
            del d[key]
    return d
于 2018-06-26T21:31:49.033 回答
7

我知道这是一个老问题,它已经有一个公认的答案,但可惜的是,公认的答案是完全错误的。

The real issue here is that the code that generates the dict uses the builtin id function as key instead of the literal string "id". So the simple, obvious and only correct solution is to fix this bug at the source : check the code that generates the dict, and replace id with "id".

于 2019-09-18T15:01:06.700 回答
-1

也许这会有所帮助:

your_dict = {("a", "b"):[1,2,3,4]}
# save
with open("file.json","w") as f:
    f.write(json.dumps(list(your_dict.items())))

# load
with open("file.json","r") as f:
    your_dict = dict([tuple((tuple(x[0]), x[1])) for x in json.loads(f.read())])
于 2019-09-18T14:36:18.870 回答
-2

例如,诺兰康纳威的回答给出了这个结果

{“b'opening_hours'”:{“b'1_from_hour'”:720,“b'1_to_hour'”:1440,“b'1_break_from_hour'”:1440,“b'1_break_to_hour'”:1440,“b'2_from_hour' “:720,“b'2_to_hour'”:1440,“b'2_break_from_hour'”:1440,“b'2_break_to_hour'”:1440,“b'3_from_hour'”:720,“b'3_to_hour'”:1440,“ b'3_break_from_hour'":1440,"b'3_break_to_hour'":1440,"b'4_from_hour'":720,"b'4_to_hour'":1440,"b'4_break_from_hour'":1440,"b'4_break_to_hour'" :1440,“b'5_from_hour'”:720,“b'5_to_hour'”:1440,“b'5_break_from_hour'”:1440,“b'5_break_to_hour'”:1440,“b'6_from_hour'”:720,“b'6_to_hour'”:1440,“b'6_break_from_hour'”:1440,“b'6_break_to_hour'”:1440 ,“b'7_from_hour'”:720,“b'7_to_hour'”:1440,“b'7_break_from_hour'”:1440,“b'7_break_to_hour'”:1440}}1440}}1440}}

而这个修正版

import time
import re
import json
from phpserialize import *


class Helpers:
   def stringify_keys(self,d):
    """Convert a dict's keys to strings if they are not."""
    for key in d.keys():
        # check inner dict
        if isinstance(d[key], dict):
            value = Helpers().stringify_keys(d[key])
        else:
            value = d[key]
        # convert nonstring to string if needed
        if not isinstance(key, str):
            try:
                d[key.decode("utf-8")] = value
            except Exception:
                try:
                    d[repr(key)] = value
                except Exception:
                    raise

            # delete old key
            del d[key]
    return d

会给这个更干净的版本..

{“opening_hours”:{“1_from_hour”:720,“1_to_hour”:1440,“1_break_from_hour”:1440,“1_break_to_hour”:1440,“2_from_hour”:720,“2_to_hour”:1440,“2_break_from_hour”:1440,“2_break_to_hour “:1440,“3_from_hour”:720,“3_to_hour”:1440,“3_break_from_hour”:1440,“3_break_to_hour”:1440,“4_from_hour”:720,“4_to_hour”:1440,“4_break_from_hour”:1440,“4_break_to_hour”: 1440,“5_from_hour”:720,“5_to_hour”:1440,“5_break_from_hour”:1440,“5_break_to_hour”:1440,“6_from_hour”:720,“6_to_hour”:1440,“6_break_from_hour”:1440,“6_break_to_hour”:1440, “7_from_hour”:720,“7_to_hour”:1440,“7_break_from_hour”:1440,“7_break_to_hour”:1440}}

于 2019-03-19T11:10:45.457 回答
-3

理想情况下,您希望清理数据,以便符合 JSON 支持的数据类型。

如果您只是想在序列化时从字典中抑制/或删除这些元素,您可以使用skipkeys参数,描述可以在json.dump部分中找到

如果 skipkeys 为 true(默认值:False),则将跳过非基本类型(str、int、float、bool、None)的 dict 键,而不是引发 TypeError。

json.dumps(obj, skipkeys=True)

这个解决方案更简洁,允许标准库为您处理错误的密钥。

警告:您必须完全理解使用这种极端方法的含义,因为这将导致不合规数据类型(如 JSON 键)的数据丢失。

于 2019-08-19T02:09:16.650 回答
-7

也许这会帮助下一个人:

strjson = json.dumps(str(dic).replace("'",'"'))
于 2015-09-17T20:30:10.013 回答