src/LinOps.jl

Fri, 08 Jan 2021 00:26:42 -0500

author
Tuomo Valkonen <tuomov@iki.fi>
date
Fri, 08 Jan 2021 00:26:42 -0500
changeset 20
8b80aa64adec
child 23
4399bf266660
permissions
-rw-r--r--

Add abstract LinOps

20
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
1 ########################################################
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
2 # Abstract Hilbert space linear operators. Does not set
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
3 # any limits on the input and output data types unlike
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
4 # the package LinearOperators.
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
5 ########################################################
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
6
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
7 __precompile__()
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
8
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
9 module LinOps
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
10
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
11 export LinOp, IdOp, AdjointOp, AdjointableOp,
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
12 calc_adjoint, calc_adjoint!, inplace!,
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
13 opnorm_estimate
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
14
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
15 # General type
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
16
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
17 abstract type LinOp{X, Y} end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
18
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
19 function inplace!(y::Y, op::LinOp{X,Y}, x::X) where {X, Y}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
20 y .= op(x)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
21 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
22
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
23 # Adjoint operator for operators that define calc_adjoint and calc_adjoint!
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
24
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
25 abstract type AdjointableOp{X, Y} <: LinOp{X,Y} end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
26
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
27 struct AdjointOp{X,Y,T<:AdjointableOp{X,Y}} <: LinOp{Y,X}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
28 op :: T
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
29 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
30
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
31 function Base.adjoint(op::T) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
32 return AdjointOp{X,Y,T}(op)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
33 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
34
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
35 function Base.adjoint(adj::AdjointOp{X,Y,T}) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
36 return adj.op
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
37 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
38
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
39 function (adj::AdjointOp{X,Y,T})(y::Y) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
40 calc_adjoint(adj, y)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
41 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
42
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
43 function inplace!(x::X, adj::AdjointOp{X,Y,T}, y::Y) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
44 calc_adjoint!(x, adj.op, y)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
45 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
46
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
47 function calc_adjoint(op::T, y::Y) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
48 @error "unimplemented"
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
49 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
50
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
51 function calc_adjoint!(x::X, adj::T, y::Y) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
52 x .= calc_adjoint(adj, y)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
53 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
54
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
55 function opnorm_estimate(adj::AdjointOp{X,Y,T}) where {X, Y, T<:AdjointableOp{X,Y}}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
56 return opnorm_estimate(adj.op)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
57 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
58
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
59 # Identity operator
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
60
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
61 struct IdOp{X} <: LinOp{X,X}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
62 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
63
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
64 function (op::IdOp{X})(x::X) where X
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
65 return x
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
66 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
67
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
68 function Base.adjoint(op::IdOp{X}) where X
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
69 return op
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
70 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
71
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
72 function opnorm_estimate(op::IdOp{X}) where X
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
73 return 1
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
74 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
75
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
76 # Matrix operator
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
77
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
78 struct MatrixOp{T<:Real}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
79 m :: AbstractArray{T, 2}
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
80 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
81
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
82 function (op::MatrixOp{T})(v::Vector{T}) where T
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
83 return op.m*v
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
84 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
85
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
86 function Base.adjoint(op::MatrixOp{T}) where T
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
87 return MatrixOp(op.m')
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
88 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
89
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
90 function opnorm_estimate(op::MatrixOp{T}) where T
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
91 return opnorm(op.m, 2)
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
92 end
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
93
8b80aa64adec Add abstract LinOps
Tuomo Valkonen <tuomov@iki.fi>
parents:
diff changeset
94 end

mercurial