Skip to content

Commit

Permalink
Merge pull request #11432 from JuliaLang/jb/curlyunion
Browse files Browse the repository at this point in the history
merge Union and UnionType; allow writing union types with `Union{ }`
  • Loading branch information
JeffBezanson committed Jun 15, 2015
2 parents 99391b3 + 34d8f63 commit 126763e
Show file tree
Hide file tree
Showing 22 changed files with 131 additions and 148 deletions.
2 changes: 1 addition & 1 deletion base/base.jl
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ ccall(:jl_get_system_hooks, Void, ())
==(w::WeakRef, v) = isequal(w.value, v)
==(w, v::WeakRef) = isequal(w, v.value)

function finalizer(o::ANY, f::Union(Function,Ptr))
function finalizer(o::ANY, f::Union{Function,Ptr})
if isimmutable(o)
error("objects of type ", typeof(o), " cannot be finalized")
end
Expand Down
14 changes: 7 additions & 7 deletions base/boot.jl
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@
# pointerfree::Bool
#end

#type UnionType <: Type
#type Union <: Type
# types::Tuple
#end

Expand Down Expand Up @@ -126,7 +126,7 @@ import Core.Intrinsics.ccall
export
# key types
Any, DataType, Vararg, ANY, NTuple,
Tuple, Type, TypeConstructor, TypeName, TypeVar, Union, UnionType, Void,
Tuple, Type, TypeConstructor, TypeName, TypeVar, Union, Void,
SimpleVector, AbstractArray, DenseArray,
# special objects
Box, Function, IntrinsicFunction, LambdaStaticData, Method, MethodTable,
Expand Down Expand Up @@ -249,7 +249,7 @@ immutable UTF8String <: AbstractString
data::Array{UInt8,1}
end

typealias ByteString Union(ASCIIString,UTF8String)
typealias ByteString Union{ASCIIString,UTF8String}

include(fname::ByteString) = ccall(:jl_load_, Any, (Any,), fname)

Expand All @@ -262,14 +262,14 @@ type WeakRef
end

TypeVar(n::Symbol) =
ccall(:jl_new_typevar, Any, (Any, Any, Any), n, Union(), Any)::TypeVar
ccall(:jl_new_typevar, Any, (Any, Any, Any), n, Union{}, Any)::TypeVar
TypeVar(n::Symbol, ub::ANY) =
(isa(ub,Bool) ?
ccall(:jl_new_typevar_, Any, (Any, Any, Any, Any), n, Union(), Any, ub)::TypeVar :
ccall(:jl_new_typevar, Any, (Any, Any, Any), n, Union(), ub::Type)::TypeVar)
ccall(:jl_new_typevar_, Any, (Any, Any, Any, Any), n, Union{}, Any, ub)::TypeVar :
ccall(:jl_new_typevar, Any, (Any, Any, Any), n, Union{}, ub::Type)::TypeVar)
TypeVar(n::Symbol, lb::ANY, ub::ANY) =
(isa(ub,Bool) ?
ccall(:jl_new_typevar_, Any, (Any, Any, Any, Any), n, Union(), lb::Type, ub)::TypeVar :
ccall(:jl_new_typevar_, Any, (Any, Any, Any, Any), n, Union{}, lb::Type, ub)::TypeVar :
ccall(:jl_new_typevar, Any, (Any, Any, Any), n, lb::Type, ub::Type)::TypeVar)
TypeVar(n::Symbol, lb::ANY, ub::ANY, b::Bool) =
ccall(:jl_new_typevar_, Any, (Any, Any, Any, Any), n, lb::Type, ub::Type, b)::TypeVar
Expand Down
2 changes: 1 addition & 1 deletion base/deepcopy.jl
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
deepcopy(x) = deepcopy_internal(x, ObjectIdDict())

deepcopy_internal(x::Union(Symbol,LambdaStaticData,TopNode,QuoteNode,
DataType,UnionType,Task),
DataType,Union,Task),
stackdict::ObjectIdDict) = x
deepcopy_internal(x::Tuple, stackdict::ObjectIdDict) =
ntuple(i->deepcopy_internal(x[i], stackdict), length(x))
Expand Down
3 changes: 3 additions & 0 deletions base/deprecated.jl
Original file line number Diff line number Diff line change
Expand Up @@ -527,3 +527,6 @@ end
function start_timer(t, d, r)
error("start_timer is deprecated. Use Timer(callback, delay, repeat) instead.")
end

const UnionType = Union
export UnionType
6 changes: 4 additions & 2 deletions base/essentials.jl
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,11 @@

abstract IO

typealias Callable Union(Function,DataType)
typealias Callable Union{Function,DataType}

const Bottom = Union()
const Bottom = Union{}

call(::Type{Union}, args...) = Union{args...}

# The real @inline macro is not available until after array.jl, so this
# internal macro splices the meta Expr directly into the function body.
Expand Down
75 changes: 38 additions & 37 deletions base/inference.jl
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ type CallStack
recurred::Bool
cycleid::Int
result
prev::Union(EmptyCallStack,CallStack)
prev::Union{EmptyCallStack,CallStack}
sv::StaticVarInfo

CallStack(ast, mod, types::ANY, prev) = new(ast, mod, types, false, 0, Bottom, prev)
Expand Down Expand Up @@ -145,7 +145,7 @@ add_tfunc(getfield(Core.Intrinsics,:ccall), 3, IInf,
if isa(t,DataType) && is((t::DataType).name,Ref.name)
t = t.parameters[1]
if is(t,Any)
return Union() # a return type of Box{Any} is invalid
return Union{} # a return type of Box{Any} is invalid
end
return t
end
Expand All @@ -158,19 +158,13 @@ add_tfunc(eval(Core.Intrinsics,:cglobal), 1, 2,
isType(t[1]) ? Ptr{t[1].parameters[1]} : Ptr))
add_tfunc(eval(Core.Intrinsics,:select_value), 3, 3,
# TODO: return Bottom if cnd is definitely not a Bool
(cnd, x, y)->Union(x,y))
(cnd, x, y)->Union{x,y})
add_tfunc(is, 2, 2, cmp_tfunc)
add_tfunc(issubtype, 2, 2, cmp_tfunc)
add_tfunc(isa, 2, 2, cmp_tfunc)
add_tfunc(isdefined, 1, IInf, (args...)->Bool)
add_tfunc(Core.sizeof, 1, 1, x->Int)
add_tfunc(nfields, 1, 1, x->Int)
add_tfunc(Union, 0, IInf,
(args...)->(if all(isType,args)
Type{Union(map(t->t.parameters[1],args)...)}
else
Type
end))
add_tfunc(_expr, 1, IInf, (args...)->Expr)
add_tfunc(method_exists, 2, 2, cmp_tfunc)
add_tfunc(applicable, 1, IInf, (f, args...)->Bool)
Expand All @@ -196,8 +190,8 @@ const typeof_tfunc = function (t)
else
Type{TypeVar(:_,t)}
end
elseif isa(t,UnionType)
Union(map(typeof_tfunc, t.types)...)
elseif isa(t,Union)
Union{map(typeof_tfunc, t.types)...}
elseif isa(t,TypeVar)
Type{t}
else
Expand All @@ -215,12 +209,12 @@ function limit_type_depth(t::ANY, d::Int, cov::Bool, vars)
return t
end
inexact = !cov && d > MAX_TYPE_DEPTH
if isa(t,UnionType)
if isa(t,Union)
t === Bottom && return t
if d > MAX_TYPE_DEPTH
R = Any
else
R = Union(map(x->limit_type_depth(x, d+1, cov, vars), t.types)...)
R = Union{map(x->limit_type_depth(x, d+1, cov, vars), t.types)...}
end
elseif isa(t,DataType)
P = t.parameters
Expand Down Expand Up @@ -254,7 +248,7 @@ const getfield_tfunc = function (A, s0, name)
return Any, false
end
end
if isa(s,UnionType)
if isa(s,Union)
return reduce(tmerge, Bottom, map(t->getfield_tfunc(A, t, name)[1], s.types)), false
end
if !isa(s,DataType)
Expand Down Expand Up @@ -376,17 +370,30 @@ has_typevars(t::ANY) = ccall(:jl_has_typevars, Cint, (Any,), t)!=0
# TODO: handle e.g. apply_type(T, R::Union(Type{Int32},Type{Float64}))
const apply_type_tfunc = function (A, args...)
if !isType(args[1])
return Type
return Any
end
headtype = args[1].parameters[1]
if isa(headtype,UnionType) || isa(headtype,TypeVar)
if isa(headtype,Union) || isa(headtype,TypeVar)
return args[1]
end
largs = length(args)
if headtype === Union
largs == 1 && return Type{Bottom}
largs == 2 && return args[2]
args = args[2:end]
if all(isType, args)
return Type{Union{map(t->t.parameters[1],args)...}}
else
return Any
end
elseif Union <: headtype
return Any
end
istuple = (headtype === Tuple)
uncertain = false
lA = length(A)
tparams = svec()
for i=2:max(lA,length(args))
for i=2:max(lA,largs)
ai = args[i]
if isType(ai)
aip1 = ai.parameters[1]
Expand Down Expand Up @@ -563,10 +570,10 @@ const isconstantref = isconstantfunc
const limit_tuple_depth = t->limit_tuple_depth_(t,0)

const limit_tuple_depth_ = function (t,d::Int)
if isa(t,UnionType)
if isa(t,Union)
# also limit within Union types.
# may have to recur into other stuff in the future too.
return Union(map(x->limit_tuple_depth_(x,d+1), t.types)...)
return Union{map(x->limit_tuple_depth_(x,d+1), t.types)...}
end
if !(isa(t,DataType) && t.name === Tuple.name)
return t
Expand Down Expand Up @@ -1088,7 +1095,7 @@ end
typealias VarTable ObjectIdDict

type StateUpdate
var::Union(Symbol,GenSym)
var::Union{Symbol,GenSym}
vtype
state::VarTable
end
Expand Down Expand Up @@ -1130,7 +1137,7 @@ function type_too_complex(t::ANY, d)
if d > MAX_TYPE_DEPTH
return true
end
if isa(t,UnionType)
if isa(t,Union)
p = t.types
elseif isa(t,DataType)
p = t.parameters
Expand Down Expand Up @@ -1158,7 +1165,7 @@ function tmerge(typea::ANY, typeb::ANY)
end
return Tuple
end
u = Union(typea, typeb)
u = Union{typea, typeb}
if length(u.types) > MAX_TYPEUNION_LEN || type_too_complex(u, 0)
# don't let type unions get too big
# TODO: something smarter, like a common supertype
Expand All @@ -1169,7 +1176,7 @@ end

issubstate(a::VarState,b::VarState) = (a.typ <: b.typ && a.undef <= b.undef)

function smerge(sa::Union(NotFound,VarState), sb::Union(NotFound,VarState))
function smerge(sa::Union{NotFound,VarState}, sb::Union{NotFound,VarState})
is(sa, NF) && return sb
is(sb, NF) && return sa
issubstate(sa,sb) && return sb
Expand All @@ -1183,7 +1190,7 @@ schanged(n::ANY, o::ANY) = is(o,NF) || (!is(n,NF) && !issubstate(n, o))
stupdate(state::Tuple{}, changes::VarTable, vars) = copy(changes)
stupdate(state::Tuple{}, changes::StateUpdate, vars) = stupdate(ObjectIdDict(), changes, vars)

function stupdate(state::ObjectIdDict, changes::Union(StateUpdate,VarTable), vars)
function stupdate(state::ObjectIdDict, changes::Union{StateUpdate,VarTable}, vars)
for i = 1:length(vars)
v = vars[i]
newtype = changes[v]
Expand All @@ -1195,7 +1202,7 @@ function stupdate(state::ObjectIdDict, changes::Union(StateUpdate,VarTable), var
state
end

function stchanged(new::Union(StateUpdate,VarTable), old, vars)
function stchanged(new::Union{StateUpdate,VarTable}, old, vars)
if is(old,())
return true
end
Expand Down Expand Up @@ -1680,7 +1687,7 @@ function typeinf_uncached(linfo::LambdaStaticData, atypes::ANY, sparams::SimpleV
end
for i = 1:length(gensym_types)
if gensym_types[i] === NF
gensym_types[i] = Union()
gensym_types[i] = Union{}
end
end

Expand Down Expand Up @@ -1883,7 +1890,7 @@ end

function sym_replace(e::ANY, from1, from2, to1, to2)
if isa(e,Symbol) || isa(e,GenSym)
return _sym_repl(e::Union(Symbol,GenSym), from1, from2, to1, to2, e)
return _sym_repl(e::Union{Symbol,GenSym}, from1, from2, to1, to2, e)
end
if isa(e,SymbolNode)
e2 = _sym_repl(e.name, from1, from2, to1, to2, e)
Expand All @@ -1907,7 +1914,7 @@ function sym_replace(e::ANY, from1, from2, to1, to2)
if isa(e2, SymbolNode)
e2 = e2.name
end
e.args[1] = e2::Union(Symbol,GenSym)
e.args[1] = e2::Union{Symbol,GenSym}
end
e.args[2] = sym_replace(e.args[2], from1, from2, to1, to2)
elseif e.head !== :line
Expand All @@ -1918,7 +1925,7 @@ function sym_replace(e::ANY, from1, from2, to1, to2)
return e
end

function _sym_repl(s::Union(Symbol,GenSym), from1, from2, to1, to2, deflt)
function _sym_repl(s::Union{Symbol,GenSym}, from1, from2, to1, to2, deflt)
for i=1:length(from1)
if is(from1[i],s)
return to1[i]
Expand Down Expand Up @@ -1979,7 +1986,7 @@ function resolve_globals(e::ANY, locals, args, from, to, env1, env2)
# remove_redundant_temp_vars can only handle Symbols
# on the LHS of assignments, so we make sure not to put
# something else there
e2 = resolve_globals(e.args[1]::Union(Symbol,GenSym), locals, args, from, to, env1, env2)
e2 = resolve_globals(e.args[1]::Union{Symbol,GenSym}, locals, args, from, to, env1, env2)
if isa(e2, GlobalRef)
# abort when trying to inline a function which assigns to a global
# variable in a different module, since `Mod.X=V` isn't allowed
Expand All @@ -1989,7 +1996,7 @@ function resolve_globals(e::ANY, locals, args, from, to, env1, env2)
# resolve_globals(e.args[2], locals, args, from, to, env1, env2))
# e.typ = e2.typ
else
e.args[1] = e2::Union(Symbol,GenSym)
e.args[1] = e2::Union{Symbol,GenSym}
e.args[2] = resolve_globals(e.args[2], locals, args, from, to, env1, env2)
end
elseif !is(e.head,:line)
Expand Down Expand Up @@ -2236,12 +2243,6 @@ function inlineable(f::ANY, e::Expr, atype::ANY, sv::StaticVarInfo, enclosing_as
isleaftype(e.typ.parameters[1])
return (e.typ.parameters[1],())
end
if is(f,Union)
union = e.typ.parameters[1]
if isa(union,UnionType) && all(isleaftype, (union::UnionType).types)
return (union,())
end
end
end
if isa(f,IntrinsicFunction)
return NF
Expand Down
2 changes: 1 addition & 1 deletion base/operators.jl
Original file line number Diff line number Diff line change
Expand Up @@ -174,7 +174,7 @@ eltype(x) = eltype(typeof(x))

# copying immutable things
copy(x::Union(Symbol,Number,AbstractString,Function,Tuple,LambdaStaticData,
TopNode,QuoteNode,DataType,UnionType)) = x
TopNode,QuoteNode,DataType,Union)) = x

# function pipelining
|>(x, f::Callable) = f(x)
Expand Down
6 changes: 3 additions & 3 deletions base/promotion.jl
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,9 @@ function typejoin(a::ANY, b::ANY)
if isa(b,TypeVar)
return typejoin(a, b.ub)
end
if isa(a,UnionType) || isa(b,UnionType)
u = Union(a, b)
if !isa(u,UnionType)
if isa(a,Union) || isa(b,Union)
u = Union{a, b}
if !isa(u,Union)
return u
end
return reduce(typejoin, Bottom, u.types)
Expand Down
2 changes: 1 addition & 1 deletion base/reducedim.jl
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,7 @@ reducedim_initarray0{T}(A::AbstractArray, region, v0::T) = reducedim_initarray0(
#
# The current scheme is basically following Steven G. Johnson's original implementation
#
promote_union(T::UnionType) = promote_type(T.types...)
promote_union(T::Union) = promote_type(T.types...)
promote_union(T) = T
function reducedim_init{S}(f, op::AddFun, A::AbstractArray{S}, region)
T = promote_union(S)
Expand Down
4 changes: 2 additions & 2 deletions base/reflection.jl
Original file line number Diff line number Diff line change
Expand Up @@ -143,8 +143,8 @@ function _methods(f::ANY,t::Array,i,lim::Integer,matching::Array{Any,1})
append!(matching, new::Array{Any,1})
else
ti = t[i]
if isa(ti, UnionType)
for ty in (ti::UnionType).types
if isa(ti, Union)
for ty in (ti::Union).types
t[i] = ty
if _methods(f,t,i-1,lim,matching) === false
t[i] = ty
Expand Down
6 changes: 3 additions & 3 deletions base/serialize.jl
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ export serialize, deserialize
const TAGS = Any[
Symbol, Int8, UInt8, Int16, UInt16, Int32, UInt32,
Int64, UInt64, Int128, UInt128, Float32, Float64, Char, Ptr,
DataType, UnionType, Function,
DataType, Union, Function,
Tuple, Array, Expr,
#LongSymbol, LongTuple, LongExpr,
Symbol, Tuple, Expr, # dummy entries, intentionally shadowed by earlier ones
Expand Down Expand Up @@ -613,9 +613,9 @@ function deserialize_expr(s::SerializationState, len)
e
end

function deserialize(s::SerializationState, ::Type{UnionType})
function deserialize(s::SerializationState, ::Type{Union})
types = deserialize(s)
Union(types...)
Union{types...}
end

function deserialize_datatype(s::SerializationState)
Expand Down
Loading

0 comments on commit 126763e

Please sign in to comment.