Find a value in JSON using Python - python

I’ve previously succeeded in parsing data from a JSON file, but now I’m facing a problem with the function I want to achieve. I have a list of names, identification numbers and birthdate in a JSON. What I want to get in Python is to be able to let a user input a name and retrieve his identification number and the birthdate (if present).
This is my JSON example file:
[
{
"id_number": "SA4784",
"name": "Mark",
"birthdate": null
},
{
"id_number": "V410Z8",
"name": "Vincent",
"birthdate": "15/02/1989"
},
{
"id_number": "CZ1094",
"name": "Paul",
"birthdate": "27/09/1994"
}
]
To be clear, I want to input "V410Z8" and get his name and his birthdate.
I tried to write some code in Python but I only succeed in searching for “id_number” and not for what is inside “id_number” for example "V410Z8".
#!/usr/bin/python
# -*- coding: utf-8 -*-
import json
database = "example.json"
data = json.loads(open(database).read())
id_number = data[0]["id_number"]
print id_number
Thank you for your support, guys :)

You have to iterate over the list of dictionaries and search for the one with the given id_number. Once you find it you can print the rest of its data and break, assuming id_number is unique.
data = [
{
"id_number": "SA4784",
"name": "Mark",
"birthdate": None
},
{
"id_number": "V410Z8",
"name": "Vincent",
"birthdate": "15/02/1989"
},
{
"id_number": "CZ1094",
"name": "Paul",
"birthdate": "27/09/1994"
}
]
for i in data:
if i['id_number'] == 'V410Z8':
print(i['birthdate'])
print(i['name'])
break
If you have control over the data structure, a more efficient way would be to use the id_number as a key (again, assuming id_number is unique):
data = { "SA4784" : {"name": "Mark", "birthdate": None},
"V410Z8" : { "name": "Vincent", "birthdate": "15/02/1989"},
"CZ1094" : {"name": "Paul", "birthdate": "27/09/1994"}
}
Then all you need to do is try to access it directly:
try:
print(data["V410Z8"]["name"])
except KeyError:
print("ID doesn't exist")
>> "Vincent"

Using lamda in Python
data = [
{
"id_number": "SA4784",
"name": "Mark",
"birthdate": None
},
{
"id_number": "V410Z8",
"name": "Vincent",
"birthdate": "15/02/1989"
},
{
"id_number": "CZ1094",
"name": "Paul",
"birthdate": "27/09/1994"
}
]
Using Lambda and filter
print(list(filter(lambda x:x["id_number"]=="CZ1094",data)))
Output
[{'id_number': 'CZ1094', 'name': 'Paul', 'birthdate': '27/09/1994'}]

You can use list comprehension:
Given
data = [
{
"id_number": "SA4784",
"name": "Mark",
"birthdate": None
},
{
"id_number": "V410Z8",
"name": "Vincent",
"birthdate": "15/02/1989"
},
{
"id_number": "CZ1094",
"name": "Paul",
"birthdate": "27/09/1994"
}
]
to get the list item(s) with id_number equal to "V410Z8" you may use:
result = [x for x in data if x["id_number"]=="V410Z8"]
result will contain:
[{'id_number': 'V410Z8', 'name': 'Vincent', 'birthdate': '15/02/1989'}]
In case the if condition is not satisfied, result will contain an empty list: []

data = [
{
"id_number": "SA4784",
"name": "Mark",
"birthdate": None
},
{
"id_number": "V410Z8",
"name": "Vincent",
"birthdate": "14/02/1989"
},
{
"id_number": "CZ1093",
"name": "Paul",
"birthdate": "26/09/1994"
}
]
list(map(lambda x:x if x["id_number"]=="cz1093" ,data)
Output should be
[{
"id_number": "CZ1094",
"name": "Paul",
"birthdate": "26/09/1994"
}]

If you are only interested in one or a subset of total results, then I'd suggest a generator function as the fastest solution, since it will not unnecessarily iterate over every item regardless, and is more memory efficient:
def gen_func(data, search_term):
for i in data:
if i['id_number'] == search_term:
yield i
You can then run the following to retrieve results for CZ1094:
foo = gen_func(data, 'CZ1094')
next(foo)
{'id_number': 'CZ1094', 'name': 'Paul', 'birthdate': '27/09/1994'}
NB: You'll need to handle StopIteration at end of iterable.

Related

Compare two separate JSONs

I have a resultant json from an intermediate stage as following
a=[{
"ID": "1201",
"SubID": "S1201",
"Information": {
"Name": "Kim",
"Age": "41"
}
}, {
"ID": "1433",
"subID": "G1433",
"Information": {
"Name": "John",
"Age": "32"
}
}]
I have another json that needs to compared with the above json
c= [{
"ID": "1201",
"SubID": "S1201"
},
{
"ID": "3211",
"subID": "G3211"
}
]
since the json object(a) in my intermediate result is present in another json(c). I want to retain only the json object which is being repeated.
expected output:
[{
"ID": "1201",
"SubID": "S1201",
"Information": {
"Name": "Kim",
"Age": "41"
}
}]
I'm not clear on what the approach to proceed with in achieving the same. Please guide me on this. Thanks.
ids = [e['ID'] for e in c]
repeated = [e for e in a if e['ID'] in ids]
print(repeated)

Find a value in a list of dictionaries

I have the following list:
{
"id":1,
"name":"John",
"status":2,
"custom_attributes":[
{
"attribute_code":"address",
"value":"st"
},
{
"attribute_code":"city",
"value":"st"
},
{
"attribute_code":"job",
"value":"test"
}]
}
I need to get the value from the attribute_code that is equal city
I've tried this code:
if list["custom_attributes"]["attribute_code"] == "city" in list:
var = list["value"]
But this gives me the following error:
TypeError: list indices must be integers or slices, not str
What i'm doing wrong here? I've read this solution and this solution but din't understood how to access each value.
Another solution, using next():
dct = {
"id": 1,
"name": "John",
"status": 2,
"custom_attributes": [
{"attribute_code": "address", "value": "st"},
{"attribute_code": "city", "value": "st"},
{"attribute_code": "job", "value": "test"},
],
}
val = next(d["value"] for d in dct["custom_attributes"] if d["attribute_code"] == "city")
print(val)
Prints:
st
Your data is a dict not a list.
You need to scan the attributes according the criteria you mentioned.
See below:
data = {
"id": 1,
"name": "John",
"status": 2,
"custom_attributes": [
{
"attribute_code": "address",
"value": "st"
},
{
"attribute_code": "city",
"value": "st"
},
{
"attribute_code": "job",
"value": "test"
}]
}
for attr in data['custom_attributes']:
if attr['attribute_code'] == 'city':
print(attr['value'])
break
output
st

How to print a specific item from within a JSON file into python

I want to print a user from a JSON list into Python that I select however I can only print all the users. How do you print a specific user? At the moment I have this which prints all the users out in a ugly format
import json
with open('Admin_sample.json') as f:
admin_json = json.load(f)
print(admin_json['staff'])
The JSON file looks like this
{
"staff": [
{
"id": "DA7153",
"name": [
"Fran\u00c3\u00a7ois",
"Ullman"
],
"department": {
"name": "Admin"
},
"server_admin": "true"
},
{
"id": "DA7356",
"name": [
"Bob",
"Johnson"
],
"department": {
"name": "Admin"
},
"server_admin": "false"
},
],
"assets": [
{
"asset_name": "ENGAGED SLOTH",
"asset_type": "File",
"owner": "DA8333",
"details": {
"security": {
"cia": [
"HIGH",
"INTERMEDIATE",
"LOW"
],
"data_categories": {
"Personal": "true",
"Personal Sensitive": "true",
"Customer Sensitive": "true"
}
},
"retention": 2
},
"file_type": "Document",
"server": {
"server_name": "ISOLATED UGUISU",
"ip": [
10,
234,
148,
52
]
}
},
{
"asset_name": "ISOLATED VIPER",
"asset_type": "File",
"owner": "DA8262",
"details": {
"security": {
"cia": [
"LOW",
"HIGH",
"LOW"
],
"data_categories": {
"Personal": "false",
"Personal Sensitive": "false",
"Customer Sensitive": "true"
}
},
"retention": 2
},
},
]
I just can't work it out. Any help would be appreciated.
Thanks.
You need to index into the staff list, e.g.:
print(admin_json['staff'][0])
I suggest reading up a bit on dictionaries in Python. Dictionary values can be set to any object: in this case, the value of the staff key is set to a list of dicts. Here's an example that will loop through all the staff members and print their names:
staff_list = admin_json['staff']
for person in staff_list:
name_parts = person['name']
full_name = ' '.join(name_parts) # combine name parts into a string
print(full_name)
Try something like this:
import json
def findStaffWithId(allStaff, id):
for staff in allStaff:
if staff["id"] == id:
return staff
return {} # no staff found
with open('Admin_sample.json') as f:
admin_json = json.load(f)
print(findStaffWithId(admin_json['staff'], "DA7356"))
You can list all the users name with
users = [user["name"] for user in admin_json['staff']]
You have two lists in this JSON file. When you try to parse it, you'll be reach a list. For example getting the first staff id:
print(admin_json['staff'][0]['id'])
This will print:
DA7153
When you use "json.loads" this will simply converts JSON file to the Python dictionary. For further info:
https://docs.python.org/3/tutorial/datastructures.html#dictionaries

Convert text file to JSON in Python

I have a text file (record.txt) with the contents like this:
12-34,Doe,John:Art101,98:History201,56
56-78,Smith,Bob,bobsmith#email.com:Calculus300,45:Economics214,78:ECE415,84
The email field is optional so it may or may not be included for each person.
This is how the JSON format should look like:
[{
"id": "12-34", "lastname": "Doe", "firstname": "John",
"classes":[{
"classname":"Art101", "grade":"98"},{
"classname":"History201","grade":"56"}]
},
{
"id": "56-78", "lastname": "Smith", "firstname": "Bob",
"email":"bobsmith#email.com,
"classes":[{
"classname":"Calculus300", "grade":"45"},{
"classname":"Economics214","grade":"78"},
"classname":"ECE415", "grade":"84"}]
}]
I am new to Python and JSON so I am having a hard time wrapping my head around how to convert the contents in such a way where the email can be an optional field and how to serialize the classes for each person as well. I was unable to convert the data into JSON after multiple attempts.
Any suggestions or advice on how to tackle this would be greatly appreciated.
Thanks in advance!
Get line and first split on : and next every element split on ,. You can use len() to check if first part has 3 or 4 elements - if 4 then there is email.
import json
text = '''12-34,Doe,John:Art101,98:History201,56
56-78,Smith,Bob,bobsmith#email.com:Calculus300,45:Economics214,78:ECE415,84'''
all_data = []
for line in text.split('\n'):
line = line.strip()
parts = line.split(':')
data = parts[0].split(',')
classes = parts[1:]
item = {
'id': data[0],
'lastname': data[1],
'firstname': data[2],
'classes': [],
}
if len(data) > 3:
item['email'] = data[3]
for class_ in classes:
name, grade = class_.split(',')
item['classes'].append({'classname': name, 'grade': grade})
all_data.append(item)
print(json.dumps(all_data, indent=2))
Result:
[
{
"id": "12-34",
"lastname": "Doe",
"firstname": "John",
"classes": [
{
"classname": "Art101",
"grade": "98"
},
{
"classname": "History201",
"grade": "56"
}
]
},
{
"id": "56-78",
"lastname": "Smith",
"firstname": "Bob",
"classes": [
{
"classname": "Calculus300",
"grade": "45"
},
{
"classname": "Economics214",
"grade": "78"
},
{
"classname": "ECE415",
"grade": "84"
}
],
"email": "bobsmith#email.com"
}
]
I am not sure how you tried.
Read each line, split based on colon (:).
Split the 0th index with (,) if length is 4 process for email. Else ignore.
Hope this is clear

How can I iterate over nested json dicts?

I've been trying to figure out how I can iterate over a json like object, so I could get a user id by its name.
json
{
"ApiSearchResult": [
{
"totalNumberResults": 55,
"type": "User",
"searchResults": [
{
"firstName": "shashank",
"name": "0o_shashank._o0",
"uid": 81097836
},
{
"firstName": "Shahnawaz",
"name": "0shahnawaz.0",
"uid": 83697589
},
{
"firstName": "Ashu",
"name": "ashu.-3",
"uid": 83646061
},
{
"bgImage": "photoalbum_491396460_user82597906-1-jpeg.jpg",
"firstName": "Garfield",
"name": "beast.boy",
"uid": 82597906
},
{
"firstName": "Bharath",
"name": "bharath_mohan69",
"uid": 80197615
},
{
"bgImage": "photoalbum_481041410_user79819261-1-jpg.jpg",
"firstName": "Wille-ICE",
"name": "blowhole",
"uid": 79819261
}
]
}
]
}
Python
def getidbyname(name):
event = response['ApiSearchResult'][0]['searchResults'][0]
for key, value in event.iteritems():
if value == name: continue
elif key == "uid":
return value
But, this won't work, I've never really worked with this many nested elements.
def getidbyname(name):
for i in data['ApiSearchResult'][0]['searchResults']:
if i['name'] == name:
return i['uid']
This might work if your response is already a python dictionary:
def getidbyname(name):
for event in data["ApiSearchResult"][0]["searchResults"]:
if event["name"] == name:
return event["uid"]
If your input is a text value, you need to use json.loads(response) to get a python dictionary out of it.

Categories