1
+ using IntervalRootFinding, IntervalArithmetic, StaticArrays, ForwardDiff, BenchmarkTools, Compat
1
2
"""
2
3
Preconditions the matrix A and b with the inverse of mid(A)
3
4
"""
4
5
function preconditioner (A:: AbstractMatrix , b:: AbstractArray )
5
6
6
7
Aᶜ = mid .(A)
7
- B = pinv (Aᶜ) # TODO If Aᶜ is singular
8
+ B = inv (Aᶜ) # TODO If Aᶜ is singular
8
9
9
10
return B* A, B* b
10
11
@@ -23,7 +24,10 @@ function newtonnd(f::Function, deriv::Function, x::IntervalBox{NUM, T}; reltol=e
23
24
if ! all (0 .∈ f (Xᴵ))
24
25
continue
25
26
end
27
+
26
28
Xᴵ¹ = copy (Xᴵ)
29
+ use_B = false
30
+
27
31
debug && (print (" Current interval popped: " ); println (Xᴵ))
28
32
29
33
if (isempty (Xᴵ))
@@ -45,22 +49,33 @@ function newtonnd(f::Function, deriv::Function, x::IntervalBox{NUM, T}; reltol=e
45
49
46
50
while true
47
51
48
- use_B = false
49
52
next_iter = false
50
53
51
54
initial_width = diam (Xᴵ)
52
55
debug && (print (" Current interval popped: " ); println (Xᴵ))
56
+ X = mid (Xᴵ)
53
57
if use_B
54
- # TODO Compute X using B in Step 19
55
- else
56
- X = mid (Xᴵ)
58
+ for i in 1 : 3
59
+ z = X .- B * f (X)
60
+ if all (z .∈ Xᴵ)
61
+ if max (abs .(f (z))... ) ≥ max (abs .(f (X))... )
62
+ break
63
+ end
64
+ X = z
65
+ else
66
+ break
67
+ end
68
+ end
69
+ if any (X .∉ Xᴵ)
70
+ X = mid .(Xᴵ)
71
+ end
57
72
end
58
73
59
74
J = SMatrix{n}{n}(deriv (Xᴵ)) # either jacobian or calculated using slopes
60
-
61
- # Xᴵ = IntervalBox((X + linear_hull(J, -f(interval.(X)) )) .∩ Xᴵ)
75
+ B, r = preconditioner (J, - f ( interval .(X)))
76
+ # Xᴵ = IntervalBox((X + linear_hull(B, r, precondition=false )) .∩ Xᴵ)
62
77
Xᴵ = IntervalBox ((X + (J \ - f (interval .(X)))) .∩ Xᴵ)
63
-
78
+ use_B = true
64
79
if (isempty (Xᴵ))
65
80
next_iter = true
66
81
break
@@ -110,3 +125,7 @@ function newtonnd(f::Function, deriv::Function, x::IntervalBox{NUM, T}; reltol=e
110
125
end
111
126
112
127
newtonnd (f:: Function , x:: IntervalBox{NUM, T} ; args... ) where {T<: AbstractFloat } where {NUM} = newtonnd (f, x-> ForwardDiff. jacobian (f,x), x; args... )
128
+
129
+ f (x, y) = SVector (x^ 2 + y^ 2 - 1 , y - 2 x)
130
+ f (X) = f (X... )
131
+ X = (0 .. 1.23 ) × (0 .. 1.123 )
0 commit comments