Home > database >  Access a dictionary key inside a dictionary key
Access a dictionary key inside a dictionary key

Time:12-26

I'm trying to make a program that gets a country name, goes to restcountries.com, gets the country's current population number, does the same thing another time, and tells if the population got bigger/smaller/same. I am a beginner at python and coding, so existing answers to similar questions were not so useful to me since they seem different than my problem. I have managed to make the code get the JSON from the site, keep it, and tell me the population number and it worked (I tested it with "Israel". But when I gave it to my pal, he wrote "Russia" and it failed. After a short investigation, I discovered restcountries.com calls Russia by the name "Russian Federation" and has a separate JSON dictionary key for common names called "common:". But I can't get to it and extract it by code. Here is the JSON from this URL: https://restcountries.com/v3/name/russia?fields=name,population [{"name":{"common":"Russia","official":"Russian Federation","nativeName":{"rus":{"official":"Российская Федерация","common":"Россия"}}},"population":144104080}]

Here is my current code:

import bs4
import urllib.request
import json

country_name = input("Choose country: ")
# Getting updated list and saving it as "json_data"
link = 'https://restcountries.com/v3/name/'   country_name   '?fields=name,population'
webpage = str(urllib.request.urlopen(link).read())
soup = bs4.BeautifulSoup(webpage, "html.parser")
json_data = soup.get_text()
# Cleans json_data from all the bullshit
clean_json = json_data[:-1][2:].replace('\\', '.') \
    .replace('.xc3.x85', 'A').replace('.xc3.xa7', 'c').replace('.xc3.xa9', 'e')

# Convert clean_json to a dictionary
loaded_json = json.loads(clean_json)


# Country search function
def search(name):
    for p in loaded_json:
        if p['name'] == name:
            return p['population']


# Choose Country, save data.
country_population = search(country_name)

datafile = open('G:\HackerU\Python\Challenges\Population\dataname.txt','w')

def save(done):
    datafile = open('G:\HackerU\Python\Challenges\Population\dataname.txt','w')
    datafile.write(country_population)
    datafile.close()
    return True

saved_population_number = datafile.read()
if saved_population_number > country_population:
    print("Population number has been decreased.")
elif saved_population_number < country_population:
    print("Population number has risen.")
elif saved_population_number == country_population:
    print("Population number stayed the same.")
else:
    print("Unknown Error.")

How do I make my code recognize a country only by its "common" name?

CodePudding user response:

It seems that there is a lot of unnecessary code here:

First of all, an API returns a JSON, therefore I don't see why you need to use bs4. You can load the JSON into a dict using json.loads.

Secondly, you don't want a string representation of the bytes object - but to decode the bytes. Therefore you can use urllib.request.urlopen(req).read().decode().

Therefore I would do something like this:

import json
import urllib.request

country_name = input("Choose country: ")
req = 'https://restcountries.com/v3/name/'   country_name   '?fields=name,population'
response = json.loads(urllib.request.urlopen(req).read().decode())[0]

Now you have the JSON response in a dictionary, and accessing response['population] gets you the country's population.

In addition, I would recommend learning about context managers and using them. For example, I would change the save function to (also, why does it return True?):

def save(country_population):
    with open('G:\HackerU\Python\Challenges\Population\dataname.txt','w') as datafile:
        datafile.write(country_population)

Good luck in the course, Python is a great language to start coding with.

CodePudding user response:

Your issue has to do with how the json data is formatted. Replace if p['name'] == name: by if p['name']['common'] == name:

  • Related