0

I have some json data similar to this...

    {
        "people": [
            {
                "name": "billy",
                "age": "12"
                 ...
                 ...
            },
            {
                "name": "karl",
                "age": "31"
                 ...
                 ...
            },
            ...
            ...
        ]
    }

At the moment I can do this to get a entry from the people list...

wantedPerson = "karl"

for person in people:
    if person['name'] == wantedPerson:
        * I have the persons entry *
        break

Is there a better way of doing this? Something similar to how we can .get('key') ? Thanks, Chris

Chris
  • 91
  • 7
  • 1
    What you are doing makes sense. – balderman Sep 27 '21 at 21:19
  • 3
    If you want to do this search multiple times, you could re-structure the data first. Otherwise there isn't any improvement to make. Keep in mind that there is no such thing as "a json object" - json *data* is parsed to create *ordinary* Python `dict`s, `list`s etc. After that, the rules are exactly the same as if you had created the data *in any other way*. – Karl Knechtel Sep 27 '21 at 21:20
  • OK thanks guys. Also, I changed object for data. – Chris Sep 27 '21 at 21:25

3 Answers3

1

Assuming you load that json data using the standard library for it, you're fairly close to optimal, perhaps you were looking for something like this:

from json import loads

text = '{"people": [{"name": "billy", "age": "12"}, {"name": "karl", "age": "31"}]}'

data = loads(text)

people = [p for p in data['people'] if p['name'] == 'karl']

If you frequently need to access this data, you might just do something like this:

all_people = {p['name']: p for p in data['people']}

print(all_people['karl'])

That is, all_people becomes a dictionary that uses the name as a key, so you can access any person in it quickly by accessing them by name. This assumes however that there are no duplicate names in your data.

Grismar
  • 27,561
  • 4
  • 31
  • 54
1

First, there's no problem with your current 'naive' approach - it's clear and efficient since you can't find the value you're looking for without scanning the list.

It seems that you refer to better as shorter, so if you want a one-liner solution, consider the following:

next((person for person in people if person.name == wantedPerson), None)

It gets the first person in the list that has the required name or None if no such person was found.

Aviv Shabi
  • 11
  • 2
0

similarly

ps =  {
        "people": [
            {
                "name": "billy",
                "age": "12"
    
            },
            {
                "name": "karl",
                "age": "31"
            },
        ]
    }

print([x for x in ps['people'] if 'karl' in x.values()])

For possible alternatives or details see e.g. # Get key by value in dictionary