How to parse json to get all values of a specific key within an array?

前端 未结 3 1874
自闭症患者
自闭症患者 2021-01-18 02:39

I\'m having trouble trying to get a list of values from a specific key inside an json array using python. Using the JSON example below, I am trying to create a list which co

相关标签:
3条回答
  • 2021-01-18 02:53

    You cannot do contents[:]["name"] since contents is a list is a dictionary with integer indexes, and you cannot access an element from it using a string name.

    To fix that, you would want to iterate over the list and get the value for key name for each item

    import json
    contents = []
    
    try:
        with open("./simple.json", 'r') as f:
            contents = json.load(f)
    except Exception as e:
        print(e)
    
    
    li = [item.get('name') for item in contents]
    print(li)
    

    The output will be

    ['Bulbasaur', 'Ivysaur']
    
    0 讨论(0)
  • 2021-01-18 03:02

    This is not a real answer to the question. The real answer is to use a list comprehension. However, you can make a class that allows you to use specifically the syntax you tried in the question. The general idea is to subclass list so that a slice like [:] returns a special view (another class) into the list. This special view will then allow retrieval and assignment from all the dictionaries simultaneously.

    class DictView:
        """
        A special class for getting and setting multiple dictionaries
        simultaneously. This class is not meant to be instantiated
        in its own, but rather in response to a slice operation on UniformDictList.
        """
        def __init__(parent, slice):
            self.parent = parent
            self.range = range(*slice.indices(len(parent)))
    
        def keys(self):
            """
            Retreives a set of all the keys that are shared across all
            indexed dictionaries. This method makes `DictView` appear as
            a genuine mapping type to `dict`.
            """
            key_set = set()
            for k in self.range:
                key_set &= self.parent.keys()
            return key_set
    
        def __getitem__(self, key):
            """
            Retreives a list of values corresponding to all the indexed
            values for `key` in the parent. Any missing key will raise
            a `KeyError`.
            """
            return [self.parent[k][key] for k in self.range]
    
        def get(self, key, default=None):
            """
            Retreives a list of values corresponding to all the indexed
            values for `key` in the parent. Any missing key will return
            `default`.
            """
            return [self.parent[k].get(key, default) for k in self.range]
    
        def __setitem__(self, key, value):
            """
            Set all the values in the indexed dictionaries for `key` to `value`.
            """
            for k in self.range:
                self.parent[k][key] = value
    
        def update(self, *args, **kwargs):
            """
            Update all the indexed dictionaries in the parent with the specified
            values. Arguments are the same as to `dict.update`.
            """
            for k in self.range:
                 self.parent[k].update(*args, **kwargs)
    
    
    class UniformDictList(list):
        def __getitem__(self, key):
            if isinstance(key, slice):
                return DictView(self, key)
            return super().__getitem__(key)
    

    Your original code would now work out of the box with just one additional wrap in UniformDictList:

    import json
    try:
        with open("./simple.json", 'r') as f:
            contents = UniformDictList(json.load(f))
    except Exception as e:
        print(e)
    
    print(contents[:]["name"])
    
    0 讨论(0)
  • 2021-01-18 03:08

    Try this with list comprehensions:

    print([d["name"] for d in contents])
    
    0 讨论(0)
提交回复
热议问题