@@ -205,59 +205,6 @@ A warning will be printed if the cotangents are not gauge-invariant, i.e. if the
205205anti-hermitian part of `U' * ΔU + Vᴴ * ΔVᴴ'`, restricted to rows `i` and columns `j` for
206206which `abs(S[i] - S[j]) < degeneracy_atol`, is not small compared to `gauge_atol`.
207207"""
208- function svd_trunc_pullback2! (
209- ΔA:: AbstractMatrix , A, USVᴴ, ΔUSVᴴ;
210- rank_atol:: Real = 0 ,
211- degeneracy_atol:: Real = default_pullback_rank_atol (USVᴴ[2 ]),
212- gauge_atol:: Real = default_pullback_gauge_atol (ΔUSVᴴ... ),
213- maxiter:: Int = 1000 ,
214- )
215-
216- # Extract the SVD components
217- U, Smat, Vᴴ = USVᴴ
218- m, n = size (U, 1 ), size (Vᴴ, 2 )
219- (m, n) == size (ΔA) || throw (DimensionMismatch ())
220- p = size (U, 2 )
221- p == size (Vᴴ, 1 ) || throw (DimensionMismatch ())
222- S = diagview (Smat)
223- p == length (S) || throw (DimensionMismatch ())
224-
225- # Extract and check the cotangents
226- ΔU, ΔSmat, ΔVᴴ = ΔUSVᴴ
227- UdΔAV, ΔU₊, ΔV₊ᴴ = check_and_prepare_svd_cotangents (
228- U, S, Vᴴ, ΔU, ΔSmat, ΔVᴴ, p; degeneracy_atol, gauge_atol
229- )
230- ΔA = mul! (ΔA, U, UdΔAV * Vᴴ, 1 , 1 ) # add the contribution to ΔA
231-
232- # The contributions from the orthogonal complement need to be treated differently
233- # ΔU and ΔVᴴ are already orthogonal to U and Vᴴ
234- if ! (iszerotangent (ΔU₊) && iszerotangent (ΔV₊ᴴ))
235- Aperp = mul! (copy (A), U, Smat * Vᴴ, - 1 , 1 )
236- x₀ = iszerotangent (ΔU₊) ? zero (U) : rdiv! (ΔU₊, Diagonal (S))
237- y₀ᴴ = iszerotangent (ΔV₊ᴴ) ? zero (Vᴴ) : ldiv! (Diagonal (S), ΔV₊ᴴ)
238- X = copy (x₀)
239- Yᴴ = copy (y₀ᴴ)
240- xₖ, xₖ₊₁ = x₀, zero (x₀)
241- yₖᴴ, yₖ₊₁ᴴ = y₀ᴴ, zero (y₀ᴴ)
242- for k in 1 : maxiter
243- xₖ₊₁ = rdiv! (mul! (xₖ₊₁, Aperp, yₖᴴ' ), Diagonal (S))
244- yₖ₊₁ᴴ = ldiv! (Diagonal (S), mul! (yₖ₊₁ᴴ, xₖ' , Aperp))
245- X .+ = xₖ₊₁
246- Yᴴ .+ = yₖ₊₁ᴴ
247- if norm (xₖ₊₁, Inf ) < degeneracy_atol && norm (yₖ₊₁ᴴ, Inf ) < degeneracy_atol
248- break
249- end
250- xₖ, xₖ₊₁ = xₖ₊₁, xₖ
251- yₖᴴ, yₖ₊₁ᴴ = yₖ₊₁ᴴ, yₖᴴ
252- if k == maxiter
253- @warn " Sylvester iteration did not converge after $k iterations, final norms: (x: $(norm (xₖ₊₁, Inf )) , y: $(norm (yₖ₊₁ᴴ, Inf )) )"
254- end
255- end
256- ΔA = mul! (ΔA, X, Vᴴ, 1 , 1 )
257- ΔA = mul! (ΔA, U, Yᴴ, 1 , 1 )
258- end
259- return ΔA
260- end
261208function svd_trunc_pullback! (
262209 ΔA:: AbstractMatrix , A, USVᴴ, ΔUSVᴴ;
263210 rank_atol:: Real = 0 ,
0 commit comments