Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add cgls-shift algorithm #853

Merged
merged 9 commits into from
Oct 14, 2024
Merged

Add cgls-shift algorithm #853

merged 9 commits into from
Oct 14, 2024

Conversation

tmigot
Copy link
Member

@tmigot tmigot commented Feb 6, 2024

  • Add a file cgls_lanczos_shift.jl in the folder src
  • Add include("cgls_lanczos_shift.jl") in src/Krylov.jl
  • Add a file test_cgls_lanczos_shift.jl in the folder test
  • Add include("test_cgls_lanczos_shift.jl") in test/runtests.jl
  • Add a CglsLanczosShiftSolver structure in src/krylov_solvers.jl
  • Add export CglsLanczosShiftSolver in src/krylov_solvers.jl
  • Update KRYLOV_SOLVERS in src/krylov_solvers.jl
  • Update the loop for (KS, fun, nsol, ...) at the end of src/krylov_solvers.jl
  • Add the docstring of CglsLanczosShiftSolver in docs/src/api.md (section Solver Types)
  • Add @docs cgls_lanczos_shift cgls_lanczos_shift! in the most relevant markdown file of docs/src/solvers
  • Add an allocation test for CGLS_LANCZOS_SHIFT in test/test_allocations.jl
  • Add :cgls_lanczos_shift in test/test_mp.jl
  • Add tests for CglsLanczosShiftSolver in test/test_solvers.jl
  • Add a test for the warm-start feature of CGLS_LANCZOS_SHIFT in test/test_warm_start.jl
  • Add a test for the verbose mode of CGLS_LANCZOS_SHIFT in test/test_verbose.jl
  • Add CGLS_LANCZOS_SHIFT in docs/src/preconditioners.md
  • Add CGLS_LANCZOS_SHIFT in docs/src/processes.md
  • Add CGLS_LANCZOS_SHIFT in docs/src/factorization-free.md (not needed for methods with multiple shifts)
  • Add CGLS_LANCZOS_SHIFT in docs/src/storage.md
  • Add a file cgls_lanczos_shift.md in the folder docs/src/examples and update docs/make.jl
  • Add CglsLanczosShiftSolver in a note of docs/src/inplace.md if the solver requires the argument memory or nshifts
  • Add a dispatch for solve! and cgls_lanczos_shift! in src/krylov_solve.jl

Copy link
Contributor

github-actions bot commented Feb 6, 2024

Package name latest stable
CaNNOLeS.jl
DCISolver.jl
FletcherPenaltySolver.jl
JSOSolvers.jl
LLSModels.jl
LinearSolve.jl
Percival.jl
RipQP.jl

expected_cgls_lanczos_shift_bytes = storage_cgls_lanczos_shift_bytes(m, k, nshifts)
(x, stats) = cgls_lanczos_shift(Ao, b, shifts) # warmup
actual_cgls_lanczos_shift_bytes = @allocated cgls_lanczos_shift(Ao, b, shifts)
@test expected_cgls_lanczos_shift_bytes ≤ actual_cgls_lanczos_shift_bytes ≤ 1.03 * expected_cgls_lanczos_shift_bytes
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@amontoison I replaced 1.02 used here by 1.03 and it sort of "fix" the tests with Julia 1.6. What do you think?

Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Try a bigger linear system ;)


#### Input arguments

* `A`: a linear operator that models a Hermitian matrix of dimension n;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A is a rectangular matrix not a square Hermitian one.


#### Keyword arguments

* `M`: linear operator that models a Hermitian positive-definite matrix of size `n` used for centered preconditioning;
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Many keyword arguments are missing in the signature at the top of the docstring (atol, rtol, ldiv, M, ...).

* `check_curvature`: if `true`, check that the curvature of the quadratic along the search direction is positive, and abort if not, unless `linesearch` is also `true`;
* `atol`: absolute stopping tolerance based on the residual norm;
* `rtol`: relative stopping tolerance based on the residual norm;
* `itmax`: the maximum number of iterations. If `itmax=0`, the default number of iterations is set to `2n`;
Copy link
Member

@amontoison amontoison Feb 23, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If A is rectangular, it's 2 × dimension(A'*A) in practice. We should verify that it's 2n and not 2m.


def_kwargs_cgls_lanczos_shift = (:(; M = I ),
:(; ldiv::Bool = false ),
:(; check_curvature::Bool = false),
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not needed because A'A + \lambda I is always SPD due to the structure. In CG-LANCZOS-SHIFT, it's just A + \lambda I.

test/test_mp.jl Outdated Show resolved Hide resolved
test/test_mp.jl Outdated Show resolved Hide resolved
@@ -4,8 +4,8 @@ function test_solvers(FC)
m = div(n, 2)
Au = A[1:m,:] # Dimension m x n
Ao = A[:,1:m] # Dimension n x m
b = Ao * ones(FC, m) # Dimension n
c = Au * ones(FC, n) # Dimension m
b = Ao * ones(FC, m) # Dimension m
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why did you modify the dimension?

Copy link
Member

@amontoison amontoison left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Good work @tmigot!

Can you explain what are the differences in terms of implementation between cgls-lanczos-shift and cg-lanczos-shift when you provide A'A as input?

It seems that you are not doing the products with A and A' so I suppose that it's a trick of the implementation.

We could add a comment about it in the docstring.
I'm curious to also compare the convergence history of cgls-shift and cg-shift on an ill-conditioned LS problem.

@amontoison
Copy link
Member

@tmigot Any update?

@tmigot
Copy link
Member Author

tmigot commented Apr 16, 2024

Hey @amontoison ! I didn't find the time to figure out the changes to add the preconditioner, so no real update.

@amontoison
Copy link
Member

@tmigot I think we should do a last pass on this PR and merge without a preconditioner.
We can add it later if needed.
What do you think?

@amontoison amontoison marked this pull request as ready for review October 14, 2024 05:23
Copy link

codecov bot commented Oct 14, 2024

Codecov Report

Attention: Patch coverage is 97.03704% with 4 lines in your changes missing coverage. Please review.

Project coverage is 94.98%. Comparing base (f5fbae9) to head (255c79e).
Report is 4 commits behind head on main.

Files with missing lines Patch % Lines
src/cgls_lanczos_shift.jl 96.33% 4 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main     #853      +/-   ##
==========================================
+ Coverage   94.43%   94.98%   +0.54%     
==========================================
  Files          44       45       +1     
  Lines        8206     8148      -58     
==========================================
- Hits         7749     7739      -10     
+ Misses        457      409      -48     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

@amontoison amontoison merged commit a4cc680 into main Oct 14, 2024
31 of 32 checks passed
@amontoison amontoison deleted the cgls-shifts branch October 14, 2024 16:52
@tmigot
Copy link
Member Author

tmigot commented Oct 15, 2024

@tmigot I think we should do a last pass on this PR and merge without a preconditioner. We can add it later if needed. What do you think?

thanks a lot @amontoison for fixing and merging this!! If you find this interesting I also have the lsqr_shifts?

@dpo
Copy link
Member

dpo commented Oct 15, 2024

@tmigot yes, please send it.

@amontoison
Copy link
Member

amontoison commented Oct 15, 2024

@tmigot Should we rename the method cgls_shift?
For lsqr_shift, it's relevant to add it if we don't duplicate the storage for each shifted system.
I remember that it was an issue.

@tmigot
Copy link
Member Author

tmigot commented Oct 16, 2024

It is a bit like cg_lanczos and cg. This implementation with shift uses the lanczos variant of cgls as well, so I would keep this name.

For lsqr_shift, it saves some memory but not as much as hoped. Still, I found the implementation useful in some tests. I will open a PR.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

3 participants