import constants import utils from tax_brackets import tax_brackets class parameters(object): """A container to hold the initial states of several simulation parameters. Play with them as you see fit and see what happens.""" def __init__(self): self.with_default_values() def with_default_values(self): # Annual expenses in USD at the start of the simulation. This # will be adjusted upwards with inflation_multiplier every year. self.initial_annual_expenses = 144300 # The average US inflation rate during the simulation. The # Fed's target rate is 2.0% as of 2020. The long term observed # average historical inflation rate in the US is 2.1%. # # Note this is a multiplier... so 1.0 would be no inflation, # 1.21 is 2.1% inflation, 0.9 is deflation, etc... self.inflation_multiplier = 1.03 # We want to be able to model social security payments not # keeping pace with inflation. Like the inflation_multiplier # above, this is a multiplier. It affect the magnitide of # social security payments year over year. self.social_security_multiplier = 1.02 # This is the average investment return rate. Asset allocation has # a large effect on this as does the overall economy. That said, # the US stock market has returned 10%/year over a large enough # time window. Our investments at Fidelity have returned 6.91% # in the lifetime they have been there. The expected return of a # 50/50 stock/bond investment mix based on historical data is 8.3%. self.investment_multiplier = 1.04 # The age at which each person will take social security # benefits in this simulation and how much she will get the # first year. Note, this benefit size increases year over # year at social_security_multiplier. This is what the social # security website estimates if we both earn $0 from 2020 on: # # Lynn's benefits: Scott's benefits: # age 62 - $21,120 age 62 - $21,420 # age 67 - $30,000 age 67 - $30,420 # age 70 - $37,200 age 70 - $37,728 # self.social_security_age = [ 0, 62, 70 ] self.initial_social_security_dollars = [ 0, 15000, 25000 ] # Tax details... the standard deduction amount and tax # brackets for ordinary income and long term capital gains. self.federal_standard_deduction_dollars = 24800 self.federal_ordinary_income_tax_brackets = tax_brackets( constants.PESSIMISTIC_FEDERAL_INCOME_TAX_BRACKETS) self.federal_dividends_and_long_term_gains_brackets = tax_brackets( constants.CURRENT_LONG_TERM_GAIN_FEDERAL_TAX_BRACKETS) return self def with_initial_annual_expenses(self, expenses): assert expenses >= 0, "You can't have negative expenses" self.initial_annual_expenses = expenses return self def get_initial_annual_expenses(self): return self.initial_annual_expenses def with_average_inflation_multiplier(self, multiplier): self.inflation_multiplier = multiplier return self def get_average_inflation_multiplier(self): return self.inflation_multiplier def with_average_social_security_multiplier(self, multiplier): self.social_security_multiplier = multiplier return self def get_average_social_security_multiplier(self): return self.social_security_multiplier def with_average_investment_return_multiplier(self, multiplier): self.investment_multiplier = multiplier return self def get_average_investment_return_multiplier(self): return self.investment_multiplier def with_initial_social_security_age_and_benefits(self, person, age, amount): assert age >= 60 and age <= 70, "age should be between 60 and 70" self.social_security_age[person] = age assert amount >= 0, "Social security won't pay negative dollars" self.initial_social_security_dollars[person] = amount return self def get_initial_social_security_age(self, person): return self.social_security_age[person] def get_initial_social_security_benefit(self, person): return self.initial_social_security_dollars[person] def with_federal_standard_deduction(self, deduction): assert deduction >= 0, "Standard deduction should be non-negative" self.federal_standard_deduction_dollars = deduction return self def get_federal_standard_deduction(self): return self.federal_standard_deduction_dollars def with_federal_ordinary_income_tax_brackets(self, brackets): self.federal_ordinary_income_tax_brackets = brackets return self def get_federal_ordinary_income_tax_brackets(self): return self.federal_ordinary_income_tax_brackets def with_federal_dividends_and_long_term_gains_income_tax_brackets(self, brackets): self.federal_dividends_and_long_term_gains_brackets = brackets; return self def get_federal_dividends_and_long_term_gains_income_tax_brackets(self): return self.federal_dividends_and_long_term_gains_brackets def dump(self): print "SIMULATION PARAMETERS" print " {:<50}: {:>14}".format("Initial year annual expenses", utils.format_money(self.initial_annual_expenses)) print " {:<50}: {:>14}".format("Annual inflation rate", utils.format_rate(self.inflation_multiplier)) print " {:<50}: {:>14}".format("Average annual investment return rate", utils.format_rate(self.investment_multiplier)) print " {:<50}: {:>14}".format("Annual social security benefit increase rate", utils.format_rate(self.social_security_multiplier)) print " {:<50}: {:>14}".format("Age at which Lynn takes social security", self.social_security_age[constants.LYNN]) print " {:<50}: {:>14}".format("Lynn's first year social security benefit", utils.format_money(self.initial_social_security_dollars[constants.LYNN])) print " {:<50}: {:>14}".format("Age at which Scott takes social security", self.social_security_age[constants.SCOTT]) print " {:<50}: {:>14}".format("Scott's first year social security benefit", utils.format_money(self.initial_social_security_dollars[constants.SCOTT])) print " Federal tax brackets [" self.federal_ordinary_income_tax_brackets.dump() print " ]" print " Federal dividend and long term gain brackets [" self.federal_dividends_and_long_term_gains_brackets.dump() print " ]" print " We assume Roth money continues to be available tax-free."