StatProfilerHTML.jl report
Generated on Thu, 26 Mar 2020 19:09:01
File source code
Line Exclusive Inclusive Code
1 export isapproxzero
2
3 Base.iszero(v::AbstractVariable) = false
4 Base.iszero(m::AbstractMonomial) = false
5 4 (0 %)
4 (0 %) samples spent in iszero
4 (100 %) (incl.) when called from uniqterms! line 107
4 (100 %) samples spent calling iszero
Base.iszero(t::AbstractTerm) = iszero(coefficient(t))
6 Base.iszero(t::AbstractPolynomial) = iszero(nterms(t))
7
8 # See https://github.com/blegat/MultivariatePolynomials.jl/issues/22
9 # avoids the call to be transfered to eqconstant
10 Base.:(==)(α::Nothing, x::APL) = false
11 Base.:(==)(x::APL, α::Nothing) = false
12 Base.:(==)(α::Dict, x::APL) = false
13 Base.:(==)(x::APL, α::Dict) = false
14 Base.:(==)(α::Nothing, x::RationalPoly) = false
15 Base.:(==)(x::RationalPoly, α::Nothing) = false
16 Base.:(==)(α::Dict, x::RationalPoly) = false
17 Base.:(==)(x::RationalPoly, α::Dict) = false
18
19 function polyeqterm(p::AbstractPolynomial, t)
20 if iszero(p)
21 iszero(t)
22 else
23 # terms/nterms ignore zero terms
24 nterms(p) == 1 && leadingterm(p) == t
25 end
26 end
27 polyeqterm(p::APL, t) = polyeqterm(polynomial(p), t)
28
29 eqconstant(α, v::AbstractVariable) = false
30 eqconstant(v::AbstractVariable, α) = false
31 function _termeqconstant(t::AbstractTermLike, α)
32 if iszero(t)
33 iszero(α)
34 else
35 α == coefficient(t) && isconstant(t)
36 end
37 end
38 eqconstant(α, t::AbstractTermLike) = _termeqconstant(t, α)
39 eqconstant(t::AbstractTermLike, α) = _termeqconstant(t, α)
40 eqconstant(α, p::APL) = polyeqterm(p, α)
41 eqconstant(p::APL, α) = polyeqterm(p, α)
42
43 function Base.:(==)(t1::AbstractTerm, t2::AbstractTerm)
44 c1 = coefficient(t1)
45 c2 = coefficient(t2)
46 if iszero(c1)
47 iszero(c2)
48 else
49 c1 == c2 && monomial(t1) == monomial(t2)
50 end
51 end
52 Base.:(==)(p::AbstractPolynomial, t::AbstractTerm) = polyeqterm(p, t)
53 Base.:(==)(t::AbstractTerm, p::AbstractPolynomial) = polyeqterm(p, t)
54
55 function compare_terms(p1::AbstractPolynomial, p2::AbstractPolynomial, isz, op)
56 i1 = 1
57 i2 = 1
58 t1 = terms(p1)
59 t2 = terms(p2)
60 while true
61 while i1 <= length(t1) && isz(coefficient(t1[i1]))
62 i1 += 1
63 end
64 while i2 <= length(t2) && isz(coefficient(t2[i2]))
65 i2 += 1
66 end
67 if i1 > length(t1) && i2 > length(t2)
68 return true
69 end
70 if i1 > length(t1) || i2 > length(t2)
71 return false
72 end
73 if !op(t1[i1], t2[i2])
74 return false
75 end
76 i1 += 1
77 i2 += 1
78 end
79 end
80
81 # Can there be zero term in TypedPolynomials ?
82 #function (==)(p1::AbstractPolynomial, p2::AbstractPolynomial)
83 # nterms(p1) != nterms(p2) && return false
84 # for (t1, t2) in zip(terms(p1), terms(p2))
85 # @assert !iszero(t1) && !iszero(t2) # There should be no zero term
86 # if t1 != t2
87 # return false
88 # end
89 # end
90 # return true
91 #end
92 Base.:(==)(p1::AbstractPolynomial, p2::AbstractPolynomial) = compare_terms(p1, p2, iszero, ==)
93
94 Base.:(==)(p::RationalPoly, q::RationalPoly) = p.num*q.den == q.num*p.den
95 # Solve ambiguity with (::PolyType, ::Any)
96 Base.:(==)(p::APL, q::RationalPoly) = p*q.den == q.num
97 Base.:(==)(q::RationalPoly, p::APL) = p == q
98 Base.:(==)(α, q::RationalPoly) = α*q.den == q.num
99 Base.:(==)(q::RationalPoly, α) = α == q
100
101 # α could be a JuMP affine expression
102 isapproxzero(α; ztol::Real=0.) = false
103 function isapproxzero(α::Number; ztol::Real=Base.rtoldefault(α, α, 0))
104 abs(α) <= ztol
105 end
106
107 isapproxzero(m::AbstractMonomialLike; kwargs...) = false
108 isapproxzero(t::AbstractTermLike; kwargs...) = isapproxzero(coefficient(t); kwargs...)
109 isapproxzero(p::APL; kwargs...) = all(isapproxzero.(terms(p); kwargs...))
110 isapproxzero(p::RationalPoly; kwargs...) = isapproxzero(p.num; kwargs...)
111
112 Base.isapprox(t1::AbstractTerm, t2::AbstractTerm; kwargs...) = isapprox(coefficient(t1), coefficient(t2); kwargs...) && monomial(t1) == monomial(t2)
113 function Base.isapprox(p1::AbstractPolynomial{S}, p2::AbstractPolynomial{T};
114 atol=0, ztol::Real=iszero(atol) ? Base.rtoldefault(S, T, 0) : atol, kwargs...) where {S, T}
115 return compare_terms(p1, p2, t -> isapproxzero(t; ztol=ztol),
116 (x, y) -> isapprox(x, y; atol=atol, kwargs...))
117 end
118
119 Base.isapprox(p::RationalPoly, q::RationalPoly; kwargs...) = isapprox(p.num*q.den, q.num*p.den; kwargs...)
120 Base.isapprox(p::RationalPoly, q::APL; kwargs...) = isapprox(p.num, q*p.den; kwargs...)
121 Base.isapprox(p::APL, q::RationalPoly; kwargs...) = isapprox(p*q.den, q.num; kwargs...)
122 Base.isapprox(q::RationalPoly{C}, α; kwargs...) where {C} = isapprox(q, constantterm(α, q.den); kwargs...)
123 Base.isapprox(α, q::RationalPoly{C}; kwargs...) where {C} = isapprox(constantterm(α, q.den), q; kwargs...)