scatter_countries = ['US', 'GB', 'FR', 'DE', 'SE', 'DK', 'NO', 'FI',
'NL', 'IT', 'ES', 'CA', 'AU', 'AT', 'CH']
# Income Gini from SWIID
income_gini = swiid.get_gini(scatter_countries, gini_type='disp',
start_year=2017, end_year=2022)
# Wealth: top 10% share from WID as a proxy for wealth concentration
wealth_top10 = wid.get_wealth_shares(
scatter_countries,
percentiles=['p90p100'],
start_year=2017, end_year=2022,
)
if not income_gini.empty and not wealth_top10.empty:
# Take most recent per country
ig = (income_gini.sort_values('year', ascending=False)
.groupby('country_code').first().reset_index())
wt = (wealth_top10.sort_values('year', ascending=False)
.groupby('country').first().reset_index())
wt = wt.rename(columns={'country': 'country_code', 'value': 'wealth_top10'})
merged = ig.merge(wt[['country_code', 'wealth_top10']], on='country_code')
if not merged.empty:
fig, ax = plt.subplots(figsize=(10, 8))
colors = [country_color(c) for c in merged['country_code']]
ax.scatter(merged['gini'], merged['wealth_top10'],
c=colors, s=120, zorder=5, edgecolors='white', linewidth=1)
annotate_countries(ax, merged['gini'].values,
merged['wealth_top10'].values,
merged['country_code'].values)
ax.set_xlabel('Disposable income Gini (SWIID)')
ax.set_ylabel('Top 10% wealth share (WID)')
ax.yaxis.set_major_formatter(mtick.PercentFormatter(1.0))
ax.set_title('Income Inequality vs. Wealth Concentration (~2020)\n'
'Nordic paradox: low income Gini, high wealth concentration',
fontsize=13)
plt.tight_layout()
save_figure(fig, '04_income_vs_wealth_gini')
plt.show()
else:
print('Could not merge income and wealth data.')
else:
print('Income Gini or wealth share data not available.')