-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathhh.jl
133 lines (105 loc) · 3.88 KB
/
hh.jl
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
# hh.jl.. solve household problem for given prices wz[,z], abz[,z], taxes, etc.
function HH_root(lambdain, sage = fag, z = 1)
global lambdaz, pcz, Consz, ellz, dis_totz, yz, Az, Savz
# EULER EQUATION: solve forward in age
lambdaz[sage,z] = lambdain
if sage < nag
for a in sage:(nag-1)
lambdaz[a+1,z] = lambdaz[a,z]/((1/(1+rho))*gamz[a,z]*(1+rz[a,z]))
end
end
# CONSUMPTION
pcz[sage:nag,z] = 1.0.+tauCz[sage:nag,z]
Consz[sage:nag,z] = (pcz[sage:nag,z].*lambdaz[sage:nag,z]).^(-sigma)
# HOURS SUPPLY
ellz[sage:nag,z] = ((wz[sage:nag,z].*(1.0.-tauWz[sage:nag,z]).*thetaz[sage:nag,z]./pcz[sage:nag,z].*(Consz[sage:nag,z].^(-1/sigma)))./parlv0[sage:nag]).^sigL
dis_totz[sage:nag,z] = (sigL/(1+sigL)).*parlv0[sage:nag].*ellz[sage:nag,z].^((1+sigL)/sigL).-parlv1[sage:nag]
# CONSUMPTION AND SAVINGS
yz[sage:nag,z] = notretz[sage:nag,z].*(wz[sage:nag,z].*(1.0.-tauWz[sage:nag,z]).*ellz[sage:nag,z].*thetaz[sage:nag,z]).+(1.0.-notretz[sage:nag,z]).*(1.0.-tauWz[sage:nag,z]).*pz[sage:nag,z].-taulz[sage:nag,z]
# ASSETS: solve forward in age
Az[1,z] = 0
if sage < nag
for a in sage:(nag-1)
Az[a+1,z] = (1+rz[a,z])*(Az[a,z]+yz[a,z]+ivz[a,z]+abz[a,z]-pcz[a,z]*Consz[a,z]) # if sage > 1 take previous age entry in Az as starting value! (i.e. has to be given globally not passed in function)
end
end
Savz[sage:nag,z] = Az[sage:nag,z].+yz[sage:nag,z].+ivz[sage:nag,z].+abz[sage:nag,z].-pcz[sage:nag,z].*Consz[sage:nag,z]
return Savz[nag,z]
end
function HH(sage = fag, z = 1, maxiter = 30, stol = 1e-10, atol = 0.1)
global HH_nonconvz
lambdaz0 = 1.0 # initialization
f0 = 1.0 # initialization
err = Inf
iter = 0
trys = 0
stepsize = 1e-6 # for numerical gradient
lambdatrys = [1.0,0.5,1.5,0.25,1.25,0.1,1.0]
maxtrys = length(lambdatrys)
while_continue = true
while (while_continue)
while_continue = false
lambdazsave = lambdaz[sage,z]
while ((err > stol)||(abs(Savz[nag,z]) > atol)) && (trys < maxtrys)
trys += 1
iterpertry = 0
lambdaz1 = lambdazsave*lambdatrys[trys]
breakwhile = false
while (err > stol) && (iterpertry < maxiter) && (breakwhile == false)
if iterpertry == 0 # Newton step for first iteration
f2 = HH_root(lambdaz1+stepsize,sage,z)
iter += 1
if !isfinite(f2)
breakwhile = true
break
end
f1 = HH_root(lambdaz1,sage,z)
iter += 1
if !isfinite(f1)
breakwhile = true
break
end
lambdaz2 = lambdaz1 - f1*stepsize/(f2-f1)
if (!isfinite(lambdaz2))||(lambdaz2<0)
breakwhile = true
break
end
else # Secant method
f1 = HH_root(lambdaz1,sage,z)
iter += 1
if !isfinite(f1)
breakwhile = true
break
end
lambdaz2 = lambdaz1 - f1*(lambdaz1-lambdaz0)/(f1-f0)
if (!isfinite(lambdaz2))||(lambdaz2<0)
breakwhile = true
break
end
end
err = abs(lambdaz2-lambdaz1)
lambdaz0 = lambdaz1
lambdaz1 = lambdaz2
f0 = f1
iterpertry += 1
end
end
end
if abs(Savz[nag,z]) > atol
HH_nonconvz[nag,z] = 1 # counter
end
end
function HHall(starttime = 1, calibinit = false, scaleA = 1)
global Az
Threads.@threads for z in starttime:ncoh
if z <= nag-fag+starttime-1
if calibinit
Az[:,z] = Av0
end
Az[nag-(z-starttime),z] = Az[nag-(z-starttime),z]*scaleA
HH(nag-(z-starttime),z)
else
HH(fag,z)
end
end
end