> Therefore there's no way the compiler can rewrite the slow version to the
> fast version.
It knows that the element type is a Feature, so it could produce:
if isa(features[i], A)
retval += evaluate(features[i]::A)
elseif isa(features[i], B)
retval += evaluate(features[i]::B)
else
retval += evaluate(features[i])
end
and it would make sense for abstract types that have few subtypes. I didn't
realize that dispatch was an order of magnitude slower than type checking.
It's easy enough to write a macro generating this expansion, too.
On Saturday, April 2, 2016 at 2:05:20 AM UTC-4, Yichao Yu wrote:
>
> On Fri, Apr 1, 2016 at 9:56 PM, Tim Wheeler <[email protected]
> <javascript:>> wrote:
> > Hello Julia Users.
> >
> > I ran into a weird slowdown issue and reproduced a minimal working
> example.
> > Maybe someone can help shed some light.
> >
> > abstract Feature
> >
> > type A <: Feature end
> > evaluate(f::A) = 1.0
> >
> > type B <: Feature end
> > evaluate(f::B) = 0.0
> >
> > function slow(features::Vector{Feature})
> > retval = 0.0
> > for i in 1 : length(features)
> > retval += evaluate(features[i])
> > end
> > retval
> > end
> >
> > function fast(features::Vector{Feature})
> > retval = 0.0
> > for i in 1 : length(features)
> > if isa(features[i], A)
> > retval += evaluate(features[i]::A)
> > else
> > retval += evaluate(features[i]::B)
> > end
> > end
> > retval
> > end
> >
> > using ProfileView
> >
> > features = Feature[]
> > for i in 1 : 10000
> > push!(features, A())
> > end
> >
> > slow(features)
> > @time slow(features)
> > fast(features)
> > @time fast(features)
> >
> > The output is:
> >
> > 0.000136 seconds (10.15 k allocations: 166.417 KB)
> > 0.000012 seconds (5 allocations: 176 bytes)
> >
> >
> > This is a HUGE difference! Am I missing something big? Is there a good
> way
> > to inspect code to figure out where I am going wrong?
>
> This is because of type instability as you will find in the performance
> tips.
> Note that slow and fast are not equivalent since the fast version only
> accept `A` or `B` but the slow version accepts any subtype of feature
> that you may ever define. Therefore there's no way the compiler can
> rewrite the slow version to the fast version.
> There are optimizations that can be applied to bring down the gap but
> there'll always be a large difference between the two.
>
> >
> >
> > Thank you in advance for any guidance.
> >
> >
> > -Tim
> >
> >
> >
> >
> >
>