@@ -16,6 +16,7 @@ mutable struct LALQMRIterable{T, xT, MT, rT, lanczosT}
16
16
G:: Vector{Givens{T}}
17
17
18
18
d:: LimitedMemoryMatrix{T, MT}
19
+ dlast:: xT
19
20
end
20
21
21
22
function lalqmr_iterable! (
@@ -54,13 +55,14 @@ function lalqmr_iterable!(
54
55
t[1 ] = resnorm
55
56
56
57
tolerance = max (reltol * resnorm, abstol)
58
+ dlast = similar (x)
57
59
58
60
return LALQMRIterable (
59
61
x,
60
62
lanczos, resnorm, tolerance,
61
63
maxiter,
62
64
t, R,
63
- G, d
65
+ G, d, dlast
64
66
)
65
67
end
66
68
@@ -83,29 +85,28 @@ function iterate(q::LALQMRIterable, n::Int=start(q))
83
85
end
84
86
gend, r = givens (Llastcol, n, n+ 1 )
85
87
push! (q. G, gend)
86
- Llastcol[end - 1 ] = r
88
+ Llastcol[end - 1 ] = r # Llastcol[end] = 0, but we don't need it
87
89
_grow_hcat! (q. R, Llastcol[1 : end - 1 ])
88
90
89
-
90
91
# Eq. 6.2, update t
91
92
push! (q. t, 0 )
92
- q. t = gend * q. t
93
+ q. t . = gend * q. t
93
94
94
95
# Eq. 6.3, calculate projection
95
96
# Dn = [Vn Un^-1 Rn^-1]
96
97
# => Dn Rn Un = Vn
97
98
RU = q. R* q. lanczos. U
98
- d = q. lanczos. V[ :, end - 1 ]
99
+ copyto! (q . dlast, view ( q. lanczos. V, :, n))
99
100
for i in 1 : size (RU, 1 )- 1
100
101
if RU[i, end ] != 0
101
- axpy! (- RU[i, end ], q. d[ :, i], d )
102
+ axpy! (- RU[i, end ], view ( q. d, :, i), q . dlast )
102
103
end
103
104
end
104
- d = d / RU[end , end ]
105
- hcat! (q. d, d )
105
+ q . dlast ./= RU[end , end ]
106
+ hcat! (q. d, q . dlast )
106
107
107
108
# iterate x_n = x_n-1 + d_n τ_n
108
- axpy! (q. t[end - 1 ], d , q. x)
109
+ axpy! (q. t[end - 1 ], q . dlast , q. x)
109
110
110
111
# Eq. 4.12, Freund 1990
111
112
q. resnorm = q. resnorm * abs (gend. s) * sqrt (n+ 1 )/ sqrt (n)
@@ -183,7 +184,8 @@ function lalqmr!(
183
184
maxiter= maxiter,
184
185
initially_zero= initially_zero,
185
186
log= log,
186
- verbose= verbose
187
+ verbose= verbose,
188
+ kwargs...
187
189
)
188
190
189
191
verbose && @printf (" === qmr ===\n %4s\t %7s\n " ," iter" ," resnorm" )
0 commit comments