Skip to content

Commit

Permalink
Make Base.ifelse a generic function (#37343)
Browse files Browse the repository at this point in the history
Allow user code to directly extend `Base.ifelse` rather than needing a
special package for it.
  • Loading branch information
c42f authored Oct 26, 2021
1 parent 2c03f81 commit 4c3ae20
Show file tree
Hide file tree
Showing 6 changed files with 21 additions and 21 deletions.
4 changes: 2 additions & 2 deletions base/boot.jl
Original file line number Diff line number Diff line change
Expand Up @@ -192,8 +192,8 @@ export
Expr, QuoteNode, LineNumberNode, GlobalRef,
# object model functions
fieldtype, getfield, setfield!, swapfield!, modifyfield!, replacefield!,
nfields, throw, tuple, ===, isdefined, eval, ifelse,
# sizeof # not exported, to avoid conflicting with Base.sizeof
nfields, throw, tuple, ===, isdefined, eval,
# ifelse, sizeof # not exported, to avoid conflicting with Base
# type reflection
<:, typeof, isa, typeassert,
# method reflection
Expand Down
2 changes: 1 addition & 1 deletion base/compiler/abstractinterpretation.jl
Original file line number Diff line number Diff line change
Expand Up @@ -1082,7 +1082,7 @@ function abstract_call_builtin(interp::AbstractInterpreter, f::Builtin, (; fargs
sv::InferenceState, max_methods::Int)
@nospecialize f
la = length(argtypes)
if f === ifelse && fargs isa Vector{Any} && la == 4
if f === Core.ifelse && fargs isa Vector{Any} && la == 4
cnd = argtypes[2]
if isa(cnd, Conditional)
newcnd = widenconditional(cnd)
Expand Down
2 changes: 1 addition & 1 deletion base/compiler/optimize.jl
Original file line number Diff line number Diff line change
Expand Up @@ -162,7 +162,7 @@ const _PURE_BUILTINS = Any[tuple, svec, ===, typeof, nfields]
const _PURE_OR_ERROR_BUILTINS = [
fieldtype, apply_type, isa, UnionAll,
getfield, arrayref, const_arrayref, isdefined, Core.sizeof,
Core.kwfunc, ifelse, Core._typevar, (<:)
Core.kwfunc, Core.ifelse, Core._typevar, (<:)
]

const TOP_TUPLE = GlobalRef(Core, :tuple)
Expand Down
2 changes: 1 addition & 1 deletion base/compiler/tfuncs.jl
Original file line number Diff line number Diff line change
Expand Up @@ -231,7 +231,7 @@ function ifelse_tfunc(@nospecialize(cnd), @nospecialize(x), @nospecialize(y))
end
return tmerge(x, y)
end
add_tfunc(ifelse, 3, 3, ifelse_tfunc, 1)
add_tfunc(Core.ifelse, 3, 3, ifelse_tfunc, 1)

function egal_tfunc(@nospecialize(x), @nospecialize(y))
xx = widenconditional(x)
Expand Down
16 changes: 16 additions & 0 deletions base/essentials.jl
Original file line number Diff line number Diff line change
Expand Up @@ -477,6 +477,22 @@ Stacktrace:
"""
sizeof(x) = Core.sizeof(x)

"""
ifelse(condition::Bool, x, y)
Return `x` if `condition` is `true`, otherwise return `y`. This differs from `?` or `if` in
that it is an ordinary function, so all the arguments are evaluated first. In some cases,
using `ifelse` instead of an `if` statement can eliminate the branch in generated code and
provide higher performance in tight loops.
# Examples
```jldoctest
julia> ifelse(1 > 2, 1, 2)
2
```
"""
ifelse(condition::Bool, x, y) = Core.ifelse(condition, x, y)

# simple Array{Any} operations needed for bootstrap
@eval setindex!(A::Array{Any}, @nospecialize(x), i::Int) = arrayset($(Expr(:boundscheck)), A, x, i)

Expand Down
16 changes: 0 additions & 16 deletions base/operators.jl
Original file line number Diff line number Diff line change
Expand Up @@ -429,22 +429,6 @@ const ≥ = >=
# which is more idiomatic:
isless(x::Real, y::Real) = x<y

"""
ifelse(condition::Bool, x, y)
Return `x` if `condition` is `true`, otherwise return `y`. This differs from `?` or `if` in
that it is an ordinary function, so all the arguments are evaluated first. In some cases,
using `ifelse` instead of an `if` statement can eliminate the branch in generated code and
provide higher performance in tight loops.
# Examples
```jldoctest
julia> ifelse(1 > 2, 1, 2)
2
```
"""
ifelse

"""
cmp(x,y)
Expand Down

2 comments on commit 4c3ae20

@vtjnash
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@nanosoldier runbenchmarks("union" || "array", vs="@2c03f811da9962738dc5b7f8ecc17ae00988f94e")

@nanosoldier
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Your benchmark job has completed - possible performance regressions were detected. A full report can be found here.

Please sign in to comment.