Skip to content

Commit d60c0ce

Browse files
committed
UPdate
1 parent bf77ad1 commit d60c0ce

1 file changed

Lines changed: 68 additions & 135 deletions

File tree

test/test_evalpoly.jl

Lines changed: 68 additions & 135 deletions
Original file line numberDiff line numberDiff line change
@@ -10,169 +10,102 @@ using Test
1010

1111
import MutableArithmetics as MA
1212

13+
function runtests()
14+
is_test(name::Symbol) = startswith("$name", "test_")
15+
@testset "$name" for name in filter(is_test, names(@__MODULE__; all = true))
16+
getfield(@__MODULE__, name)()
17+
end
18+
return
19+
end
20+
1321
function alloc_test(f::F, expected_upper_bound::Integer) where {F<:Function}
1422
f() # compile
1523
measured_allocations = @allocated f()
1624
@test measured_allocations <= expected_upper_bound
1725
return
1826
end
1927

20-
abstract type OpSignature end
28+
_is_op_to(::Any) = false
2129

22-
struct RegularSignature <: OpSignature end
23-
24-
struct ToSignature <: OpSignature end
25-
26-
function signature_type_of(
27-
::Union{typeof(MA.operate),typeof(MA.operate!),typeof(MA.operate!!)},
28-
)
29-
return RegularSignature()
30-
end
30+
_is_op_to(::Union{typeof(MA.operate_to!),typeof(MA.operate_to!!)}) = true
3131

32-
function signature_type_of(
33-
::Union{typeof(MA.operate_to!),typeof(MA.operate_to!!)},
34-
)
35-
return ToSignature()
36-
end
37-
38-
function op_may_modify_first_argument(op::Function)
39-
return (op != MA.operate) & (signature_type_of(op) == RegularSignature())
40-
end
41-
42-
function op_is_allowed_for_arithmetic(
43-
::typeof(evalpoly),
32+
function _should_test(
4433
::Union{typeof(MA.operate!),typeof(MA.operate_to!)},
4534
::Type{F},
46-
) where {F<:Any}
35+
) where {F}
4736
return MA.mutability(F) == MA.IsMutable()
4837
end
4938

50-
function op_is_allowed_for_arithmetic(
51-
::typeof(evalpoly),
52-
::Union{typeof(MA.operate),typeof(MA.operate!!),typeof(MA.operate_to!!)},
53-
::Type{F},
54-
) where {F<:Any}
55-
return true
56-
end
57-
58-
function allowed_allocated_byte_count(
59-
::typeof(evalpoly),
60-
::Union{typeof(MA.operate),typeof(MA.operate!),typeof(MA.operate!!)},
61-
::Type{F},
62-
) where {F<:Any}
63-
return @allocated zero(F)
64-
end
65-
66-
function allowed_allocated_byte_count(
67-
::typeof(evalpoly),
68-
::Union{typeof(MA.operate_to!),typeof(MA.operate_to!!)},
69-
::Type{F},
70-
) where {F<:Any}
71-
return @allocated nothing
39+
_should_test(op, ::Type{F}) where {F} = true
40+
41+
function test_evalpoly()
42+
for F in (BigFloat, Rational{Int}, Float64, Float32, Int)
43+
for op in (
44+
MA.operate,
45+
MA.operate!,
46+
MA.operate_to!,
47+
MA.operate!!,
48+
MA.operate_to!!,
49+
)
50+
if _should_test(op, F)
51+
_test_evalpoly(op, F, "vector")
52+
_test_evalpoly(op, F, "tuple")
53+
end
54+
end
55+
end
56+
return
7257
end
7358

74-
const evalpoly_supported_arithmetics =
75-
(BigFloat, Rational{Int}, Float64, Float32, Int)
76-
77-
const evalpoly_operations =
78-
(MA.operate, MA.operate!, MA.operate_to!, MA.operate!!, MA.operate_to!!)
79-
80-
@testset "evalpoly with $op and $F" for F in evalpoly_supported_arithmetics,
81-
op in evalpoly_operations
82-
83-
op_is_allowed_for_arithmetic(evalpoly, op, F) || continue
84-
85-
sig = signature_type_of(op)
86-
59+
function _test_evalpoly(op, ::Type{F}, collection_type) where {F}
8760
if MA.mutability(F) == MA.IsMutable()
88-
@testset "empty coefficients $collection_type" for collection_type in
89-
("vector", "tuple")
90-
out = one(F)
91-
x = one(F)
92-
backup = MA.copy_if_mutable(x)
93-
coefs = F[]
94-
if collection_type == "tuple"
95-
coefs = ()
96-
end
97-
98-
# Check that the result value is OK
99-
if sig == RegularSignature()
100-
@test iszero(@inferred op(evalpoly, x, coefs))
101-
elseif sig == ToSignature()
102-
@test iszero(@inferred op(out, evalpoly, x, coefs))
103-
else
104-
error("unexpected")
105-
end
106-
107-
# Check that the arguments are unmodified
108-
op_may_modify_first_argument(op) || @test backup == x
61+
out = one(F)
62+
x = one(F)
63+
backup = MA.copy_if_mutable(x)
64+
coefs = collection_type == "tuple" ? () : F[]
65+
if _is_op_to(op)
66+
@test iszero(@inferred op(out, evalpoly, x, coefs))
67+
else
68+
@test iszero(@inferred op(evalpoly, x, coefs))
69+
end
70+
if op == MA.operate || _is_op_to(op)
71+
@test backup == x
10972
end
11073
end
111-
112-
@testset "exact values: $degree, $x_int" for degree in 0:4, x_int in -5:5
74+
for degree in 0:4, x_int in -5:5
11375
coefs_int = rand(-6:6, degree + 1)
114-
11576
coefs = map(F, coefs_int)
11677
x = F(x_int)
117-
78+
backup = MA.copy_if_mutable(x)
11879
reference = evalpoly(x, coefs)
119-
12080
@test reference == evalpoly(x_int, coefs_int)
121-
122-
@testset "collection type $collection_type" for collection_type in
123-
("vector", "tuple")
124-
out = zero(F)
125-
if collection_type == "vector"
126-
coefs_arg = coefs
127-
else
128-
coefs_arg = (coefs...,)
129-
end
130-
if sig == RegularSignature()
131-
out = @inferred op(evalpoly, x, coefs_arg)
132-
elseif sig == ToSignature()
133-
out = @inferred op(out, evalpoly, x, coefs_arg)
134-
else
135-
error("unexpected")
136-
end
137-
138-
# Check that the result value is OK
139-
@test reference == out
140-
141-
# Check that the arguments are unmodified
142-
if op_may_modify_first_argument(op)
143-
x = F(x_int)
144-
else
145-
@test x == F(x_int)
146-
end
147-
@test coefs == map(F, coefs_int)
81+
out = zero(F)
82+
coefs_arg = collection_type == "vector" ? coefs : (coefs...,)
83+
if _is_op_to(op)
84+
@test reference == @inferred op(out, evalpoly, x, coefs_arg)
85+
else
86+
@test reference == @inferred op(evalpoly, x, coefs_arg)
87+
end
88+
if op == MA.operate || _is_op_to(op)
89+
@test x == backup
14890
end
91+
@test coefs == map(F, coefs_int)
14992
end
150-
151-
@testset "allocation" begin
152-
byte_cnt = allowed_allocated_byte_count(evalpoly, op, F)
153-
coefs_tuple = map(F, (0, 1, 0, 1, 1))
154-
@testset "collection type $collection_type" for collection_type in
155-
("vector", "tuple")
156-
if collection_type == "vector"
157-
coefs = collect(coefs_tuple)
158-
else
159-
coefs = coefs_tuple
160-
end
161-
local tested_fun
162-
if sig == RegularSignature()
163-
tested_fun = let x = one(F), coefs = coefs
164-
() -> op(evalpoly, x, coefs)
165-
end
166-
elseif sig == ToSignature()
167-
tested_fun = let o = one(F), x = one(F), coefs = coefs
168-
() -> op(o, evalpoly, x, coefs)
169-
end
170-
else
171-
error("unexpected")
172-
end
173-
alloc_test(tested_fun, byte_cnt)
93+
byte_cnt = _is_op_to(op) ? 0 : @allocated(zero(F))
94+
coefs = if collection_type == "vector"
95+
F[0, 1, 0, 1, 1]
96+
else
97+
F.((0, 1, 0, 1, 1))
98+
end
99+
let o = one(F), x = one(F), coefs = coefs
100+
if _is_op_to(op)
101+
alloc_test(() -> op(o, evalpoly, x, coefs), byte_cnt)
102+
else
103+
alloc_test(() -> op(evalpoly, x, coefs), byte_cnt)
174104
end
175105
end
106+
return
176107
end
177108

178109
end # TestEvalPoly
110+
111+
TestEvalPoly.runtests()

0 commit comments

Comments
 (0)