An empty array triggered a bug caused by not dispatching correctly, which I worked around with isempty. But I could have also overriden promote_op and not had to deal with empty arrays as a special case.
> On 24 Sep. 2016, at 8:15 am, Pablo Zubieta <pablof...@gmail.com> wrote: > > Sheehan, are you planning on doing a lot of operations with empty arrays? On > 0.5 with your example > > julia> [Foo(1), Foo(2)] + [Foo(1), Foo(0)] > 2-element Array{Foo,1}: > Foo{Float64}(1.0) > Foo{Int64}(1) > > The problem is empty arrays, when the type cannot be inferred broadcast uses > the types of each element to build the array. When there are no elements it > doesn't know what type to choose. > > On Friday, September 23, 2016 at 11:47:11 PM UTC+2, Sheehan Olver wrote: > OK, here's a better example of the issue: in the following code I would want > it to return an Array(Foo,0), not an Array(Any,0). Is this possible without > overriding promote_op? > > julia> immutable Foo{T} > > x::T > > end > > > > julia> import Base.+ > > > > julia> +(a::Foo,b::Foo) = (a.x==b.x? Foo(1.0) : Foo(1)) > > + (generic function with 164 methods) > > > > julia> Array(Foo{Float64},0)+Array(Foo{Float64},0) > > 0-element Array{Any,1} > > > > > > > > > On Friday, September 23, 2016 at 10:54:03 PM UTC+10, Pablo Zubieta wrote: > In julia 0.5 the following should work without needing doing anything to > promote_op > > import Base.+ > immutable Foo end > +(a::Foo, b::Foo) =1.0 > Array{Foo}(0) + Array{Foo}(0)) > > promote_op is supposed to be an internal method that you wouldn't need to > override. If it is not working i because the operation you are doing is most > likely not type stable. So instead of specializing it you could try to remove > any type instabilities in the method definitions over your types. > > On Friday, September 23, 2016 at 5:35:05 AM UTC+2, Sheehan Olver wrote: > > The subject says it all: it looks like one can override promote_op to support > the following behaviour: > > julia> import Base.+ > > > > julia> immutable Foo end > > WARNING: Method definition (::Type{Main.Foo})() in module Main at REPL[5]:1 > overwritten at REPL[10]:1. > > > > julia> +(a::Foo,b::Foo) = 1.0 > > + (generic function with 164 methods) > > > > julia> Base.promote_op(::typeof(+),::Type{Foo},::Type{Foo}) = Float64 > > > > julia> Array(Foo,0) + Array(Foo,0) > > 0-element Array{Float64,1} > > > > Is this documented somewhere? What if we want to override /, -, etc., is the > solution to write a promote_op for each case?