From b84f2805c4e3207c2ea842b33963265cfb6f2859 Mon Sep 17 00:00:00 2001 From: David Widmann Date: Thu, 14 Mar 2024 00:22:13 +0100 Subject: [PATCH 1/2] Make `isless`, `<`, `>`, `<=`, and `>=` consistent with `==` and `isequal` --- src/dual.jl | 22 ++++++++++++++++++---- 1 file changed, 18 insertions(+), 4 deletions(-) diff --git a/src/dual.jl b/src/dual.jl index 2ca4683f..3e1e5e73 100644 --- a/src/dual.jl +++ b/src/dual.jl @@ -384,17 +384,31 @@ end # Before PR#481 this loop ran over this list: # BINARY_PREDICATES = Symbol[:isequal, :isless, :<, :>, :(==), :(!=), :(<=), :(>=)] # Not a minimal set, as Base defines some in terms of others. -for pred in [:isless, :<, :>, :(<=), :(>=)] +for pred in [:<, :>] + predeq = Symbol(pred, :(=)) @eval begin @define_binary_dual_op( Base.$(pred), - $(pred)(value(x), value(y)), - $(pred)(value(x), y), - $(pred)(x, value(y)), + $(pred)(value(x), value(y)) || (value(x) == value(y) && $(pred)(partials(x), partials(y))), + $(pred)(value(x), y) || (value(x) == y && $(pred)(partials(x), zero(partials(x)))), + $(pred)(x, value(y)) || (x == value(y) && $(pred)(zero(partials(y)), partials(y))), + ) + @define_binary_dual_op( + Base.$(predeq), + $(pred)(value(x), value(y)) || (value(x) == value(y) && $(predeq)(partials(x), partials(y))), + $(pred)(value(x), y) || (value(x) == y && $(predeq)(partials(x), zero(partials(x)))), + $(pred)(x, value(y)) || (x == value(y) && $(predeq)(zero(partials(y)), partials(y))), ) end end +@define_binary_dual_op( + Base.isless, + isless(value(x), value(y)) || (isequal(value(x), value(y)) && isless(partials(x), partials(y))), + isless(value(x), y) || (isequal(value(x), y) && isless(partials(x), zero(partials(x)))), + isless(x, value(y)) || (isequal(x, value(y)) && isless(zero(partials(y)), partials(y))), +) + Base.iszero(x::Dual) = iszero(value(x)) && iszero(partials(x)) # shortcut, equivalent to x == zero(x) for pred in [:isequal, :(==)] From bfd8c956aa24be25e7d1e0e7934634170d763fc3 Mon Sep 17 00:00:00 2001 From: David Widmann Date: Sat, 16 Mar 2024 02:06:39 +0100 Subject: [PATCH 2/2] Fix tests --- test/DualTest.jl | 30 ++++++++++++++++++++---------- 1 file changed, 20 insertions(+), 10 deletions(-) diff --git a/test/DualTest.jl b/test/DualTest.jl index f921081b..bc67aef1 100644 --- a/test/DualTest.jl +++ b/test/DualTest.jl @@ -262,43 +262,53 @@ ForwardDiff.:≺(::Type{OuterTestTag}, ::Type{TestTag}) = false end @test isless(Dual{TestTag()}(1, PARTIALS), Dual{TestTag()}(2, PARTIALS2)) - @test !(isless(Dual{TestTag()}(1, PARTIALS), Dual{TestTag()}(1, PARTIALS2))) + @test isless(Dual{TestTag()}(1, PARTIALS), Dual{TestTag()}(1, PARTIALS2)) === isless(PARTIALS, PARTIALS2) + @test !(isless(Dual{TestTag()}(1, PARTIALS), Dual{TestTag()}(1, PARTIALS))) @test !(isless(Dual{TestTag()}(2, PARTIALS), Dual{TestTag()}(1, PARTIALS2))) @test isless(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS), Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS2), NESTED_PARTIALS2)) - @test !(isless(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS), Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2))) + @test isless(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS), Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS2)) === isless(NESTED_PARTIALS, NESTED_PARTIALS2) + @test !(isless(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS), Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS))) @test !(isless(Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS), NESTED_PARTIALS), Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2))) @test Dual{TestTag()}(1, PARTIALS) < Dual{TestTag()}(2, PARTIALS2) - @test !(Dual{TestTag()}(1, PARTIALS) < Dual{TestTag()}(1, PARTIALS2)) + @test (Dual{TestTag()}(1, PARTIALS) < Dual{TestTag()}(1, PARTIALS2)) === (PARTIALS < PARTIALS2) + @test !(Dual{TestTag()}(1, PARTIALS) < Dual{TestTag()}(1, PARTIALS)) @test !(Dual{TestTag()}(2, PARTIALS) < Dual{TestTag()}(1, PARTIALS2)) @test Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) < Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS2), NESTED_PARTIALS2) - @test !(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) < Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2)) + @test (Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) < Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS2)) === (NESTED_PARTIALS < NESTED_PARTIALS2) + @test !(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) < Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS)) @test !(Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS), NESTED_PARTIALS) < Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2)) @test Dual{TestTag()}(1, PARTIALS) <= Dual{TestTag()}(2, PARTIALS2) - @test Dual{TestTag()}(1, PARTIALS) <= Dual{TestTag()}(1, PARTIALS2) + @test (Dual{TestTag()}(1, PARTIALS) <= Dual{TestTag()}(1, PARTIALS2)) === (PARTIALS <= PARTIALS2) + @test Dual{TestTag()}(1, PARTIALS) <= Dual{TestTag()}(1, PARTIALS) @test !(Dual{TestTag()}(2, PARTIALS) <= Dual{TestTag()}(1, PARTIALS2)) @test Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) <= Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS2), NESTED_PARTIALS2) - @test Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) <= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2) + @test (Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) <= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS2)) === (NESTED_PARTIALS <= NESTED_PARTIALS2) + @test Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) <= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) @test !(Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS), NESTED_PARTIALS) <= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2)) @test Dual{TestTag()}(2, PARTIALS) > Dual{TestTag()}(1, PARTIALS2) - @test !(Dual{TestTag()}(1, PARTIALS) > Dual{TestTag()}(1, PARTIALS2)) + @test (Dual{TestTag()}(1, PARTIALS) > Dual{TestTag()}(1, PARTIALS2)) === (PARTIALS > PARTIALS2) + @test !(Dual{TestTag()}(1, PARTIALS) > Dual{TestTag()}(1, PARTIALS)) @test !(Dual{TestTag()}(1, PARTIALS) > Dual{TestTag()}(2, PARTIALS2)) @test Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS), NESTED_PARTIALS) > Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2) - @test !(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) > Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2)) + @test (Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) > Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS2)) === (NESTED_PARTIALS > NESTED_PARTIALS2) + @test !(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) > Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS)) @test !(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) > Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS2), NESTED_PARTIALS2)) @test Dual{TestTag()}(2, PARTIALS) >= Dual{TestTag()}(1, PARTIALS2) - @test Dual{TestTag()}(1, PARTIALS) >= Dual{TestTag()}(1, PARTIALS2) + @test (Dual{TestTag()}(1, PARTIALS) >= Dual{TestTag()}(1, PARTIALS2)) === (PARTIALS >= PARTIALS2) + @test Dual{TestTag()}(1, PARTIALS) >= Dual{TestTag()}(1, PARTIALS) @test !(Dual{TestTag()}(1, PARTIALS) >= Dual{TestTag()}(2, PARTIALS2)) @test Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS), NESTED_PARTIALS) >= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2) - @test Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) >= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS2), NESTED_PARTIALS2) + @test (Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) >= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS2)) === (NESTED_PARTIALS >= NESTED_PARTIALS2) + @test Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) >= Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) @test !(Dual{TestTag()}(Dual{TestTag()}(1, M_PARTIALS), NESTED_PARTIALS) >= Dual{TestTag()}(Dual{TestTag()}(2, M_PARTIALS2), NESTED_PARTIALS2)) @test isnan(Dual{TestTag()}(NaN, PARTIALS))