def test_top_share(): ''' Test of top share calculation ''' ineq = Inequality(dist, pop_weights, ability_weights, S, J) top_share = ineq.top_share(0.05) assert np.allclose(top_share, 0.285714286)
def wealth_moments_table(base_ss, base_params, table_format=None, path=None): ''' Creates table with moments of the wealth distribution from the model and SCF data. Args: base_ss (dictionary): SS output from baseline run base_params (OG-USA Specifications class): baseline parameters object table_format (string): format to return table in: 'csv', 'tex', 'excel', 'json', if None, a DataFrame is returned path (string): path to save table to Returns: table (various): table in DataFrame or string format or `None` if saved to disk ''' table_dict = { 'Moment': [ 'Share 0-25%', 'Share 25-50%', 'Share 50-70%', 'Share 70-80%', 'Share 80-90%', 'Share 90-99%', 'Share 99-100%', 'Gini Coefficient', 'var(ln(Wealth))' ], 'Data': [], 'Model': [] } base_ineq = Inequality(base_ss['bssmat_splus1'], base_params.omega_SS, base_params.lambdas, base_params.S, base_params.J) base_values = [ 1 - base_ineq.top_share(0.75), base_ineq.top_share(0.75) - base_ineq.top_share(0.5), base_ineq.top_share(0.5) - base_ineq.top_share(0.3), base_ineq.top_share(0.3) - base_ineq.top_share(0.2), base_ineq.top_share(0.2) - base_ineq.top_share(0.1), base_ineq.top_share(0.1) - base_ineq.top_share(0.01), base_ineq.top_share(0.01), base_ineq.gini(), base_ineq.var_of_logs() ] table_dict['Model'].extend(base_values) # get moments from Survey of Consumer Finances data scf = wealth.get_wealth_data() table_dict['Data'] = wealth.compute_wealth_moments(scf, base_params.lambdas) # Make df with dict so can use pandas functions table_df = pd.DataFrame.from_dict(table_dict) table = save_return_table(table_df, table_format, path, precision=3) return table
def calc_moments(ss_output, p): """ This function calculates moments from the SS output that correspond to the data moments used for estimation. Args: ss_output = dictionary, variables from SS of model p (OG-USA Specifications object): model parameters Returns: model_moments (array-like): Array of model moments """ # Create Inequality object wealth_ineq = Inequality(ss_output["bssmat_splus1"], p.omega_SS, p.lambdas, p.S, p.J) # wealth moments # moments are: bottom 25% of wealth, next 25% share of wealth # (25-50 pctile), next 20% share of wealth (50-70 pctile), # next 10% share (70-80 pctile), next 10% share (80-90 pctile), # next 9% share (90-99 pctile), top 1% share, # gini coefficient, variance of log wealth model_moments = np.array([ 1 - wealth_ineq.top_share(0.75), wealth_ineq.top_share(0.75) - wealth_ineq.top_share(0.50), wealth_ineq.top_share(0.50) - wealth_ineq.top_share(0.30), wealth_ineq.top_share(0.30) - wealth_ineq.top_share(0.20), wealth_ineq.top_share(0.20) - wealth_ineq.top_share(0.10), wealth_ineq.top_share(0.10) - wealth_ineq.top_share(0.01), wealth_ineq.top_share(0.01), wealth_ineq.gini(), wealth_ineq.var_of_logs(), ]) return model_moments
def inequality_plot( base_tpi, base_params, reform_tpi=None, reform_params=None, var='c_path', ineq_measure='gini', pctiles=None, plot_type='levels', num_years_to_plot=50, start_year=DEFAULT_START_YEAR, vertical_line_years=None, plot_title=None, path=None): ''' Plot measures of inequality over the time path. Args: base_tpi (dictionary): TPI output from baseline run base_params (OG-USA Specifications class): baseline parameters object reform_tpi (dictionary): TPI output from reform run reform_params (OG-USA Specifications class): reform parameters object var(string): name of variable to plot ineq_measure (string): inequality measure to plot, can be: 'gini': Gini coefficient 'var_of_logs': variance of logs 'pct_ratio': percentile ratio 'top_share': top share of total pctiles (tuple or None): percentiles for percentile ratios (numerator, denominator) or percentile for top share (not required for Gini or var_of_logs) plot_type (string): type of plot, can be: 'pct_diff': plots percentage difference between baselien and reform ((reform-base)/base) 'diff': plots difference between baseline and reform (reform-base) 'levels': plot variables in model units num_years_to_plot (integer): number of years to include in plot start_year (integer): year to start plot vertical_line_years (list): list of integers for years want vertical lines at plot_title (string): title for plot path (string): path to save figure to Returns: fig (Matplotlib plot object): plot of inequality measure ''' assert isinstance(start_year, (int, np.integer)) assert (isinstance(num_years_to_plot, int)) # Make sure both runs cover same time period if reform_tpi: assert (base_params.start_year == reform_params.start_year) assert ineq_measure in ['gini', 'var_of_logs', 'pct_ratio', 'top_share'] if (ineq_measure == 'pct_ratio') | (ineq_measure == 'top_share'): assert pctiles year_vec = np.arange(start_year, start_year + num_years_to_plot) # Check that reform included if doing pct_diff or diff plot if plot_type == 'pct_diff' or plot_type == 'diff': assert (reform_tpi is not None) fig1, ax1 = plt.subplots() base_values = np.zeros(num_years_to_plot) for t in range(num_years_to_plot): idx = (t + start_year) - base_params.start_year ineq = Inequality( base_tpi[var][idx, :, :], base_params.omega[idx, :], base_params.lambdas, base_params.S, base_params.J) if ineq_measure == 'gini': base_values[t] = ineq.gini() ylabel = r'Gini Coefficient' elif ineq_measure == 'var_of_logs': base_values[t] = ineq.var_of_logs() ylabel = r'var(ln(' + VAR_LABELS[var] + r'))' elif ineq_measure == 'pct_ratio': base_values[t] = ineq.ratio_pct1_pct2(pctiles[0], pctiles[1]) ylabel = r'Ratio' elif ineq_measure == 'top_share': base_values[t] = ineq.top_share(pctiles) ylabel = r'Share of Total ' + VAR_LABELS[var] if reform_tpi: reform_values = np.zeros_like(base_values) for t in range(num_years_to_plot): idx = (t + start_year) - base_params.start_year ineq = Inequality( reform_tpi[var][idx, :, :], reform_params.omega[idx, :], reform_params.lambdas, reform_params.S, reform_params.J) if ineq_measure == 'gini': reform_values[t] = ineq.gini() elif ineq_measure == 'var_of_logs': reform_values[t] = ineq.var_of_logs() elif ineq_measure == 'pct_ratio': reform_values[t] = ineq.ratio_pct1_pct2(pctiles[0], pctiles[1]) elif ineq_measure == 'top_share': reform_values[t] = ineq.top_share(pctiles) if plot_type == 'pct_diff': plot_var = (reform_values - base_values) / base_values ylabel = r'Pct. change' plt.plot(year_vec, plot_var) elif plot_type == 'diff': plot_var = reform_values - base_values ylabel = r'Difference' plt.plot(year_vec, plot_var) elif plot_type == 'levels': plt.plot(year_vec, base_values, label='Baseline') if reform_tpi: plt.plot(year_vec, reform_values, label='Reform') # vertical markers at certain years if vertical_line_years: for yr in vertical_line_years: plt.axvline(x=yr, linewidth=0.5, linestyle='--', color='k') plt.xlabel(r'Year $t$') plt.ylabel(ylabel) if plot_title: plt.title(plot_title, fontsize=15) vals = ax1.get_yticks() if plot_type == 'pct_diff': ax1.set_yticklabels(['{:,.2%}'.format(x) for x in vals]) plt.xlim((base_params.start_year - 1, base_params.start_year + num_years_to_plot)) plt.legend(loc=9, bbox_to_anchor=(0.5, -0.15), ncol=2) if path: fig_path1 = os.path.join(path) plt.savefig(fig_path1, bbox_inches="tight") else: return fig1 plt.close()
def ineq_table(base_ss, base_params, reform_ss=None, reform_params=None, var_list=['cssmat'], table_format=None, path=None): ''' Creates table with various inequality measures in the model steady-state. Args: base_ss (dictionary): SS output from baseline run base_params (OG-USA Specifications class): baseline parameters object reform_ss (dictionary): SS output from reform run reform_params (OG-USA Specifications class): reform parameters object var_list (list): names of variable to use in table table_format (string): format to return table in: 'csv', 'tex', 'excel', 'json', if None, a DataFrame is returned path (string): path to save table to Returns: table (various): table in DataFrame or string format or `None` if saved to disk ''' table_dict = { 'Steady-State Variable': [], 'Inequality Measure': [], 'Baseline': [] } if reform_ss: table_dict['Reform'] = [] table_dict['% Change'] = [] for i, v in enumerate(var_list): base_ineq = Inequality(base_ss[v], base_params.omega_SS, base_params.lambdas, base_params.S, base_params.J) if reform_ss: reform_ineq = Inequality(reform_ss[v], reform_params.omega_SS, reform_params.lambdas, reform_params.S, reform_params.J) table_dict['Steady-State Variable'].extend( [VAR_LABELS[v], '', '', '', '']) table_dict['Inequality Measure'].extend([ 'Gini Coefficient', 'Var of Logs', '90/10 Ratio', 'Top 10% Share', 'Top 1% Share' ]) base_values = np.array([ base_ineq.gini(), base_ineq.var_of_logs(), base_ineq.ratio_pct1_pct2(0.90, 0.10), base_ineq.top_share(0.1), base_ineq.top_share(0.01) ]) table_dict['Baseline'].extend(list(base_values)) if reform_ss: reform_values = np.array([ reform_ineq.gini(), reform_ineq.var_of_logs(), reform_ineq.ratio_pct1_pct2(0.90, 0.10), reform_ineq.top_share(0.1), reform_ineq.top_share(0.01) ]) table_dict['Reform'].extend(list(reform_values)) table_dict['% Change'].extend( list(((reform_values - base_values) / base_values) * 100)) # Make df with dict so can use pandas functions table_df = pd.DataFrame.from_dict(table_dict) table = save_return_table(table_df, table_format, path, precision=3) return table