Say, I have a type hierarchy
abstract A
immutable B <: A end
immutable C <: A end
The constructor of A
follows factory pattern:
function A(x::Int)
if x > 0
B()
else
C()
end
end
It returns different subtypes based on the input as expected. However, it is also type unstable as I cannot find a way to force the return type to be A
.
So, is it bad to have factory pattern here? Does the type instability only affects immutable types rather than mutable types, since the latter is reference type anyway.
Do I have to opt to the parametric type for this?
immutable D{T <: A}
type::T
end
function D(x::Int)
if x > 0
D(B())
else
D(C())
end
end
It feels a bit bad.
Actually, how bad it is to have type unstable functions? Is is worthwhile to trade for better code readability?
Alternatively, should I define typealias A Union{B,C}
instead?
Well, you could do this:
but it doesn't help:
You can't create instances of an abstract type. Moreover, in current julia, any abstract type is automatically "type-unstable," meaning that the compiler can't generate optimized code for it. So there is no such thing as "forcing the return type to be A" and then having that somehow make the function type-stable (in the sense of obtaining great performance).
You can implement a type-stable factory pattern, but the output type should be determined by the input types, not the input values. For example:
is a type-stable constructor for objects of the
A
hierarchy.If there aren't obvious types to use to signal your intent, you can always use
Val
: