def test_broyden(self): """ Test solving with Broyden's method, instead of the default Gauss-Seidel """ # pylint: disable=too-many-statements model = Model() model.set_var_default(0) model.vars('Y', 'YD', 'Ts', 'Td', 'Hs', 'Hh', 'Gs', 'Cs', 'Cd', 'Ns', 'Nd') model.set_param_default(0) Gd = model.param('Gd') W = model.param('W') alpha1 = model.param('alpha1') alpha2 = model.param('alpha2') theta = model.param('theta') model.add('Cs = Cd') model.add('Gs = Gd') model.add('Ts = Td') model.add('Ns = Nd') model.add('YD = (W*Ns) - Ts') model.add('Td = theta * W * Ns') model.add('Cd = alpha1*YD + alpha2*Hh(-1)') model.add('Hs - Hs(-1) = Gd - Td') model.add('Hh - Hh(-1) = YD - Cd') model.add('Y = Cs + Gs') model.add('Nd = Y/W') # setup default parameter values Gd.value = 20. W.value = 1.0 alpha1.value = 0.6 alpha2.value = 0.4 theta.value = 0.2 debuglist = [] model.solve(iterations=100, threshold=1e-4, debuglist=debuglist, method='broyden') soln = round_solution(model.solutions[-1], decimals=1) print(soln) self.assertTrue(numpy.isclose(38.5, soln['Y'])) self.assertTrue(numpy.isclose(7.7, soln['Ts'])) self.assertTrue(numpy.isclose(30.8, soln['YD'])) self.assertTrue(numpy.isclose(18.5, soln['Cs'])) self.assertTrue(numpy.isclose(12.3, soln['Hs'])) self.assertTrue(numpy.isclose(12.3, soln['Hh'])) self.assertTrue(numpy.isclose(0, soln['_Hs__1'])) self.assertTrue(numpy.isclose(0, soln['_Hh__1']))
# The determination of employment. # We now have 11 equations and 11 unknowns. **Each of the eleven unknowns has been set on the left-hand side of an equation** (This implies that we can use the Gauss-Seidel algorithm to iterate to a solution, convergence is not guaranteed but we can try.) # ###### Solve # We have set the default for all of the variables to 0, and that will be used as an initial solution. # In[15]: model.solve(iterations=100, threshold=1e-4) # In[16]: prev = round_solution(model.solutions[-2], decimals=1) solution = round_solution(model.solutions[-1], decimals=1) print("Y : " + str(solution['Y'])) print("T : " + str(solution['Ts'])) print("YD : " + str(solution['YD'])) print("C : " + str(solution['Cs'])) print("Hs-Hs(-1) : " + str(solution['Hs'] - prev['Hs'])) print("Hh-Hh(-1) : " + str(solution['Hh'] - prev['Hh'])) print("H : " + str(solution['Hh'])) # ### The code for the full model # To make the model easier to manipulate, I will encapsulate model creation into a single function. # In[17]:
model.add('Gs = Gd') model.add('Ts = Td') model.add('Ns = Nd') model.add('YD = (W*Ns) - Ts') model.add('Td = theta * W * Ns') model.add('Cd = alpha1*YD + alpha2*Hh(-1)') model.add('Hs - Hs(-1) = Gd - Td') model.add('Hh - Hh(-1) = YD - Cd') model.add('Y = Cs + Gs') model.add('Nd = Y/W') return model start = time.clock() sim = create_model() for _ in xrange(100): sim.solve(iterations=100, threshold=1e-5) prev_soln = sim.solutions[-2] soln = sim.solutions[-1] if is_close(prev_soln, soln, atol=1e-3): break end = time.clock() print "elapsed time = " + str(end - start) print round_solution(sim.solutions[-1], decimals=1)
def test_full_model(self): """ Test by implementing a model This model is taken from the book Monetary Economics 2ed, Godley and Lavoie, 2012 Chapter 3, The Simplest Model wtih Government Money Model SIM """ # pylint: disable=too-many-statements model = Model() model.set_var_default(0) model.vars('Y', 'YD', 'Ts', 'Td', 'Hs', 'Hh', 'Gs', 'Cs', 'Cd', 'Ns', 'Nd') model.set_param_default(0) Gd = model.param('Gd') W = model.param('W') alpha1 = model.param('alpha1') alpha2 = model.param('alpha2') theta = model.param('theta') model.add('Cs = Cd') model.add('Gs = Gd') model.add('Ts = Td') model.add('Ns = Nd') model.add('YD = (W*Ns) - Ts') model.add('Td = theta * W * Ns') model.add('Cd = alpha1*YD + alpha2*Hh(-1)') model.add('Hs - Hs(-1) = Gd - Td') model.add('Hh - Hh(-1) = YD - Cd') model.add('Y = Cs + Gs') model.add('Nd = Y/W') # setup default parameter values Gd.value = 20. W.value = 1.0 alpha1.value = 0.6 alpha2.value = 0.4 theta.value = 0.2 model.solve(iterations=200, threshold=1e-3) soln = round_solution(model.solutions[-1], decimals=1) self.assertTrue(numpy.isclose(38.5, soln['Y'])) self.assertTrue(numpy.isclose(7.7, soln['Ts'])) self.assertTrue(numpy.isclose(30.8, soln['YD'])) self.assertTrue(numpy.isclose(18.5, soln['Cs'])) self.assertTrue(numpy.isclose(12.3, soln['Hs'])) self.assertTrue(numpy.isclose(12.3, soln['Hh'])) self.assertTrue(numpy.isclose(0, soln['_Hs__1'])) self.assertTrue(numpy.isclose(0, soln['_Hh__1'])) model.solve(iterations=200, threshold=1e-3) soln = round_solution(model.solutions[-1], decimals=1) self.assertTrue(numpy.isclose(47.9, soln['Y'])) self.assertTrue(numpy.isclose(9.6, soln['Ts'])) self.assertTrue(numpy.isclose(38.3, soln['YD'])) self.assertTrue(numpy.isclose(27.9, soln['Cs'])) self.assertTrue(numpy.isclose(22.7, soln['Hs'])) self.assertTrue(numpy.isclose(22.7, soln['Hh'])) self.assertTrue(numpy.isclose(12.3, soln['_Hs__1'])) self.assertTrue(numpy.isclose(12.3, soln['_Hh__1'])) # Now run until the solutions themselves converge prev_soln = model.solutions[-1] converges = False for _ in range(100): model.solve(iterations=100, threshold=1e-3) # run until we converge soln = model.solutions[-1] if is_close(prev_soln, soln, atol=1e-3): converges = True break prev_soln = soln self.assertTrue(converges) prev = round_solution(model.solutions[-2], decimals=1) soln = round_solution(model.solutions[-1], decimals=1) self.assertTrue(numpy.isclose(100, soln['Y'])) self.assertTrue(numpy.isclose(20, soln['Ts'])) self.assertTrue(numpy.isclose(80, soln['YD'])) self.assertTrue(numpy.isclose(80, soln['Cs'])) self.assertTrue(numpy.isclose(0, soln['Hs'] - prev['Hs'])) self.assertTrue(numpy.isclose(0, soln['Hh'] - prev['Hh']))
def test_full_model(self): """ Test by implementing a model This model is taken from the book Monetary Economics 2ed, Godley and Lavoie, 2012 Chapter 3, The Simplest Model wtih Government Money Model SIM """ # pylint: disable=too-many-statements model = Model() model.set_var_default(0) model.vars('Y', 'YD', 'Ts', 'Td', 'Hs', 'Hh', 'Gs', 'Cs', 'Cd', 'Ns', 'Nd') model.set_param_default(0) Gd = model.param('Gd') W = model.param('W') alpha1 = model.param('alpha1') alpha2 = model.param('alpha2') theta = model.param('theta') model.add('Cs = Cd') model.add('Gs = Gd') model.add('Ts = Td') model.add('Ns = Nd') model.add('YD = (W*Ns) - Ts') model.add('Td = theta * W * Ns') model.add('Cd = alpha1*YD + alpha2*Hh(-1)') model.add('Hs - Hs(-1) = Gd - Td') model.add('Hh - Hh(-1) = YD - Cd') model.add('Y = Cs + Gs') model.add('Nd = Y/W') # setup default parameter values Gd.value = 20. W.value = 1.0 alpha1.value = 0.6 alpha2.value = 0.4 theta.value = 0.2 model.solve(iterations=200, threshold=1e-3) soln = round_solution(model.solutions[-1], decimals=1) self.assertTrue(numpy.isclose(38.5, soln['Y'])) self.assertTrue(numpy.isclose(7.7, soln['Ts'])) self.assertTrue(numpy.isclose(30.8, soln['YD'])) self.assertTrue(numpy.isclose(18.5, soln['Cs'])) self.assertTrue(numpy.isclose(12.3, soln['Hs'])) self.assertTrue(numpy.isclose(12.3, soln['Hh'])) model.solve(iterations=200, threshold=1e-3) soln = round_solution(model.solutions[-1], decimals=1) self.assertTrue(numpy.isclose(47.9, soln['Y'])) self.assertTrue(numpy.isclose(9.6, soln['Ts'])) self.assertTrue(numpy.isclose(38.3, soln['YD'])) self.assertTrue(numpy.isclose(27.9, soln['Cs'])) self.assertTrue(numpy.isclose(22.7, soln['Hs'])) self.assertTrue(numpy.isclose(22.7, soln['Hh'])) # Now run until the solutions themselves converge prev_soln = model.solutions[-1] converges = False for _ in xrange(100): model.solve(iterations=100, threshold=1e-3) # run until we converge soln = model.solutions[-1] if is_close(prev_soln, soln, atol=1e-3): converges = True break prev_soln = soln self.assertTrue(converges) prev = round_solution(model.solutions[-2], decimals=1) soln = round_solution(model.solutions[-1], decimals=1) self.assertTrue(numpy.isclose(100, soln['Y'])) self.assertTrue(numpy.isclose(20, soln['Ts'])) self.assertTrue(numpy.isclose(80, soln['YD'])) self.assertTrue(numpy.isclose(80, soln['Cs'])) self.assertTrue(numpy.isclose(0, soln['Hs'] - prev['Hs'])) self.assertTrue(numpy.isclose(0, soln['Hh'] - prev['Hh']))
model.add('Ts = Td') # 3.3 model.add('Ns = Nd') # 3.4 model.add('YD = (W*Ns) - Ts') # 3.5 model.add('Td = theta * W * Ns') # 3.6, theta < 1.0 model.add('Cd = alpha1*YDe + alpha2*Hh(-1)') # 3.7E model.add('Hs - Hs(-1) = Gd - Td') # 3.8 model.add('Hh - Hh(-1) = YD - Cd') # 3.9 model.add('Hd - Hs(-1) = YDe - Cd') # 3.18 model.add('Y = Cs + Gs') # 3.10 model.add('Nd = Y/W') # 3.11 model.add('YDe = YD(-1)') # 3.20 return model steady_state = create_simex_model() steady_state.set_parameters({'alpha1': 0.6, 'alpha2': 0.4, 'theta': 0.2}) steady_state.set_parameters({'Gd': 20, 'W': 1}) steady_state.variables['YD'].value = steady_state.evaluate('Gd*(1-theta)') for _ in range(100): steady_state.solve(iterations=100, threshold=1e-5) if is_close(steady_state.solutions[-2], steady_state.solutions[-1], atol=1e-4): break print(round_solution(steady_state.solutions[-1], decimals=1))
model.add('YD = (W*Ns) - Ts'); model.add('Td = theta * W * Ns'); model.add('Cd = alpha1*YD + alpha2*Hh(-1)'); model.add('Hs - Hs(-1) = Gd - Td'); model.add('Hh - Hh(-1) = YD - Cd'); model.add('Y = Cs + Gs'); model.add('Nd = Y/W'); model.solve(iterations=100, threshold=1e-4); prev = round_solution(model.solutions[-2], decimals=1) solution = round_solution(model.solutions[-1], decimals=1) print ("Y : " + str(solution['Y'])) print ("T : " + str(solution['Ts'])) print ("YD : " + str(solution['YD'])) print ("C : " + str(solution['Cs'])) print ("Hs-Hs(-1) : " + str(solution['Hs'] - prev['Hs'])) print ("Hh-Hh(-1) : " + str(solution['Hh'] - prev['Hh'])) print ("H : " + str(solution['Hh']))
'Rb': 0.03, 'Pbl': 20}) sim.set_parameters({'alpha1': 0.8, 'alpha2': 0.2, 'chi': 0.1, 'lambda20': 0.44196, 'lambda22': 1.1, 'lambda23': 1, 'lambda24': 0.03, 'lambda30': 0.3997, 'lambda32': 1, 'lambda33': 1.1, 'lambda34': 0.03, 'theta': 0.1938}) sim.set_parameters({'G': 20, 'Rbar': 0.03, 'Pblbar': 20}) for _ in xrange(100): sim.solve(iterations=100, threshold=1e-5) prev_soln = sim.solutions[-2] soln = sim.solutions[-1] if is_close(prev_soln, soln, atol=1e-3): break end = time.clock() print "elapsed time = " + str(end-start) print round_solution(sim.solutions[-1], decimals=1)
model.add('Ts = Td') # 3.3 model.add('Ns = Nd') # 3.4 model.add('YD = (W*Ns) - Ts') # 3.5 model.add('Td = theta * W * Ns') # 3.6, theta < 1.0 model.add('Cd = alpha1*YDe + alpha2*Hh(-1)') # 3.7E model.add('Hs - Hs(-1) = Gd - Td') # 3.8 model.add('Hh - Hh(-1) = YD - Cd') # 3.9 model.add('Hd - Hs(-1) = YDe - Cd') # 3.18 model.add('Y = Cs + Gs') # 3.10 model.add('Nd = Y/W') # 3.11 model.add('YDe = YD(-1)') # 3.20 return model steady_state = create_simex_model() steady_state.set_parameters({'alpha1': 0.6, 'alpha2': 0.4, 'theta': 0.2}) steady_state.set_parameters({'Gd': 20, 'W': 1}) steady_state.variables['YD'].value = steady_state.evaluate('Gd*(1-theta)') for _ in xrange(100): steady_state.solve(iterations=100, threshold=1e-5) if is_close(steady_state.solutions[-2], steady_state.solutions[-1], atol=1e-4): break print round_solution(steady_state.solutions[-1], decimals=1)