Skip to content

Commit

Permalink
some type safety for Fix
Browse files Browse the repository at this point in the history
Disallows any type `Fix{x}` where `!(x isa Int) || (x < 0)`.

Follows up on PR JuliaLang#54653.

The goals are similar as in the closed PR JuliaLang#56518, but less ambitious.

I hope it's not too late in the release cycle to consider this change
as it seems not to be invasive or disruptive.
  • Loading branch information
nsajko committed Feb 8, 2025
1 parent baf8124 commit f8fb3a6
Show file tree
Hide file tree
Showing 2 changed files with 10 additions and 10 deletions.
14 changes: 6 additions & 8 deletions base/operators.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1170,17 +1170,15 @@ A type representing a partially-applied version of a function `f`, with the argu
`Fix{1}(Fix{2}(f, 4), 4)` fixes the first and second arg, while `Fix{2}(Fix{1}(f, 4), 4)`
fixes the first and third arg.
"""
struct Fix{N,F,T} <: Function
struct Fix{N,F,T,NTuple{N,Nothing}<:NTup<:NTuple{N,Nothing}} <: Function
f::F
x::T

function Fix{N}(f::F, x) where {N,F}
if !(N isa Int)
throw(ArgumentError(LazyString("expected type parameter in `Fix` to be `Int`, but got `", N, "::", typeof(N), "`")))
elseif N < 1
throw(ArgumentError(LazyString("expected `N` in `Fix{N}` to be integer greater than 0, but got ", N)))
if N < 1
throw(ArgumentError("expected `N` in `Fix{N}` to be integer greater than 0, but got 0"))
end
new{N,_stable_typeof(f),_stable_typeof(x)}(f, x)
new{N,_stable_typeof(f),_stable_typeof(x),NTuple{N,Nothing}}(f, x)
end
end

Expand All @@ -1196,12 +1194,12 @@ end
"""
Alias for `Fix{1}`. See [`Fix`](@ref Base.Fix).
"""
const Fix1{F,T} = Fix{1,F,T}
const Fix1{F,T} = Fix{1,F,T,NTuple{1,Nothing}}

"""
Alias for `Fix{2}`. See [`Fix`](@ref Base.Fix).
"""
const Fix2{F,T} = Fix{2,F,T}
const Fix2{F,T} = Fix{2,F,T,NTuple{2,Nothing}}


"""
Expand Down
6 changes: 4 additions & 2 deletions test/functional.jl
Original file line number Diff line number Diff line change
Expand Up @@ -348,9 +348,11 @@ end
@test f() == 'a'
end
@testset "Dummy-proofing" begin
@test_throws TypeError Fix{1, <:Any, <:Any, Union{}}
@test_throws Exception Fix{-1}
@test_throws ArgumentError("expected `N` in `Fix{N}` to be integer greater than 0, but got 0") Fix{0}(>, 1)
@test_throws ArgumentError("expected type parameter in `Fix` to be `Int`, but got `0.5::Float64`") Fix{0.5}(>, 1)
@test_throws ArgumentError("expected type parameter in `Fix` to be `Int`, but got `1::UInt64`") Fix{UInt64(1)}(>, 1)
@test_throws TypeError Fix{0.5}
@test_throws TypeError Fix{UInt64(1)}
end
@testset "Specialize to structs not in `Base`" begin
struct MyStruct
Expand Down

0 comments on commit f8fb3a6

Please sign in to comment.