遍历带有条件的JSON对象

3

在这里,我遇到了一些关于循环遍历json对象content的困难。 该json文件如下:

[{'archived': False,
  'cache_ttl': None,
  'collection': {'archived': False,
   'authority_level': None,
   'color': '#509EE3',
   'description': None,
   'id': 525,
   'location': '/450/',
   'name': 'eaf',
   'namespace': None,
   'personal_owner_id': None,
   'slug': 'eaf'},
  'collection_id': 525,
  'collection_position': None,
  'created_at': '2022-01-06T20:51:17.06376Z',
  'creator_id': 1,
  'database_id': 4,
  }, ... ]

我希望能够遍历列表中的每个字典,检查集合是否为空,然后对于每个集合,如果位置等于'/450/',则将该字典添加到列表中。

我的代码如下。

content = json.loads(res.text)

for q in content:
  if q['collection']:
    for col in q['collection']:
      if col['location'] == '/450/':
        data.append(q)
  
print(data) 

玩弄了一下之后,我要么得到了ValueError: too many values to unpack (expected 2),要么得到了TypeError: string indices must be integers。非常感谢对我的帮助。

免责声明: 我之前以列表推导式的形式写了它,而且它运行得非常好,但是现在不再起作用,因为我现在需要检查collection是否为空。 我先前的写法如下:

content = [ x for x in content if x['collection']['location'] == '/450/']

1
你会收到 TypeError: string indices must be integers 的错误提示,因为 col 是一个字符串,而你试图执行 col['location'] - John Gordon
4个回答

3

这应该适用于你:

for q in content:
    if q['collection']['location'] == '/450/':
        data.append(q)
  
print(data)

如果您使用for col in q['collection']for循环,您只是遍历q['collection']内部的键,因此cols = ['archived', 'authority_level', ...]

1

从您之前的列表推导式中可以看出,"location"q["collection"]中的一个键。 当您编写以下代码时:

for col in q["collection"]

您正在遍历q["collection"]中的键。其中一个键是"location"。您的for循环似乎遍历了不必要的内容:

if q['collection'] and "location" in q["collection"] and q["collection"]["location"]  == "/450/":
    data.append(q)

1
不需要遍历集合对象,因为它是一个字典,只需要检查位置属性。此外,如果“collection”或“location”属性不存在,则使用dict.get(key)函数而不是dict[key],因为后者会在找不到键时引发KeyError异常,而get()返回None值。
content = [{'archived': False,
        'cache_ttl': None,
        'collection': {'archived': False,
                       'authority_level': None,
                       'color': '#509EE3',
                       'description': None,
                       'id': 525,
                       'location': '/450/',
                       'name': 'eaf',
                       'namespace': None,
                       'personal_owner_id': None,
                       'slug': 'eaf'},
        'collection_id': 525,
        'collection_position': None,
        'created_at': '2022-01-06T20:51:17.06376Z',
        'creator_id': 1,
        'database_id': 4,
        },
       {'foo': None}
       ]

#content = json.loads(res.text)
data = []
for q in content:
    c = q.get('collection')
    if c and c.get('location') == '/450/':
        data.append(q)
  
print(data)

输出:

[{'archived': False, 'cache_ttl': None, 'collection': { 'location': '/450/', 'name': 'eaf', 'namespace': None }, ...}]

1

你的代码循环次数过多

当你检查col['location'] = "/450/"时,在第二个条件语句处会出现错误TypeError: string indices must be integers

这是因为集合对象中并不是所有的令牌都有子对象,你无法通过它们的键来获取数据

查看你的旧代码修改后的代码,以更深入地了解。

# Your old json datas
content  = [{'archived': False,
  'cache_ttl': None,
  'collection': {'archived': False,
   'authority_level': None,
   'color': '#509EE3',
   'description': None,
   'id': 525,
   'location': '/450/',
   'name': 'eaf',
   'namespace': None,
   'personal_owner_id': None,
   'slug': 'eaf'},
  'collection_id': 525,
  'collection_position': None,
  'created_at': '2022-01-06T20:51:17.06376Z',
  'creator_id': 1,
  'database_id': 4,
  } ]

data = []
for q in content:
    if q['collection']:
        for col in q['collection']: 
            if col['location'] == '/450/': # The first object in collection object is [archived] which is a string, this causes the program to throw error
                data.append(q)
  
print(data) 

这是修改后的代码。
# Your json datas
json_datas = [{'archived': False,
  'cache_ttl': None,
  'collection': {'archived': False,
   'authority_level': None,
   'color': '#509EE3',
   'description': None,
   'id': 525,
   'location': '/450/',
   'name': 'eaf',
   'namespace': None,
   'personal_owner_id': None,
   'slug': 'eaf'},
  'collection_id': 525,
  'collection_position': None,
  'created_at': '2022-01-06T20:51:17.06376Z',
  'creator_id': 1,
  'database_id': 4,
  } ]


list_data = [] # Your list data in which appends the json data if the location is /450/

for data in json_datas: # Getting each Json data
  if len(data["collection"]): # Continue if the length of collection is not 0 [NOTE: 0 = False, 1 or more = True]
    if data['collection']['location'] == "/450/": # Check the location
      list_data.append(data) # Append if true


print(list_data)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接