import pandas as pd
nes = pd.read_csv("nes2020_subset.csv")Day 4 — Solutions
pandas and APIs
Exercise 1 — Inspecting a DataFrame
print(nes.head())
print(nes.columns.tolist())
print(nes.shape) # (rows, columns)
print(nes.describe())shape is a tuple, describe() gives count/mean/std/min/quartiles/max for each numeric column.
Exercise 2 — Filtering
high_biden = nes[nes["ft_biden"] > 80]
print(len(high_biden))
print(high_biden["ft_trump"].mean())Boolean indexing: nes["ft_biden"] > 80 returns a Series of True/False, and nes[...] keeps the rows where it’s True. .mean() on the filtered ft_trump column gives you the conditional average.
Exercise 3 — Summary by group
result = nes.groupby("freetrade")["ft_police"].mean()
print(result)groupby splits the data into chunks based on the column you pass, and .mean() summarizes each chunk. Selecting ["ft_police"] before .mean() keeps only that column in the result.
Exercise 4 — Creating a new column
nes["biden_minus_trump"] = nes["ft_biden"] - nes["ft_trump"]
print(nes["biden_minus_trump"].mean())
print((nes["biden_minus_trump"] > 0).sum())Subtracting two Series produces a new Series, pandas handles the row alignment for you. (series > 0).sum() counts True values (because True acts like 1 in arithmetic).
Exercise 5 — A small DataFrame from scratch
import pandas as pd
data = {
"policy": ["education", "healthcare", "defense", "infrastructure", "climate"],
"budget_b": [82, 1670, 850, 244, 75],
"approve_pct": [68, 54, 49, 71, 62],
}
df = pd.DataFrame(data)
# 1. Sort by budget descending
print(df.sort_values("budget_b", ascending=False))
# 2. Filter to high approval
print(df[df["approve_pct"] > 60])
# 3. Mean approval
print(df["approve_pct"].mean()) policy budget_b approve_pct
1 healthcare 1670 54
2 defense 850 49
3 infrastructure 244 71
0 education 82 68
4 climate 75 62
policy budget_b approve_pct
0 education 82 68
3 infrastructure 244 71
4 climate 75 62
60.8
sort_values doesn’t mutate the DataFrame — it returns a new sorted view (use inplace=True if you want to overwrite).
Exercise 6 — Hitting an API
import requests
url = "https://api.census.gov/data/2020/dec/pl?get=NAME,P1_001N&for=state:*"
r = requests.get(url)
print(r.status_code) # should be 200
data = r.json()
print(data[:5])The Census API returns a list of lists — first row is headers (["NAME", "P1_001N", "state"]), each subsequent row is one state.
Exercise 7 — Putting it together: API → DataFrame
import requests
import pandas as pd
url = "https://api.census.gov/data/2020/dec/pl?get=NAME,P1_001N&for=state:*"
r = requests.get(url)
data = r.json()
# First row is column names; rest are data
df = pd.DataFrame(data[1:], columns=data[0])
# Convert population column to integer
df["P1_001N"] = df["P1_001N"].astype(int)
# Sort and print top 10
top10 = df.sort_values("P1_001N", ascending=False).head(10)
print(top10[["NAME", "P1_001N"]])pd.DataFrame(data[1:], columns=data[0]) builds a DataFrame from the rows (excluding the header) and assigns the header as column names. The Census API returns numeric values as strings, so .astype(int) converts them so sorting and arithmetic work correctly.