Oh.. I did not try @code_native (to be honest I can't read the output 
anyway...). Thanks a lot for the precision. The whole discussion is clearer 
now. 

On Wednesday, September 30, 2015 at 8:38:49 AM UTC-4, Mauro wrote:
>
> If you look at @code_native you'll see that the branch which still 
> exists in code_warntype is eliminated. 
>
> On Wed, 2015-09-30 at 14:06, Matt <matth...@gmail.com <javascript:>> 
> wrote: 
> > Also, both Stefan and you mention that the branching is eliminated in 
> the 
> > first method. But if if I use on the first version 
> > 
> > @code_warntype  f(rand(10, 10)) 
> > 
> > Body: 
> > 
> >   begin  # none, line 2: 
> > 
> >       (Base.println)(Base.STDOUT,"I'm an array")::Any # line 3: 
> > 
> >       unless 2 === 1::Bool goto 0 # line 4: 
> > 
> >       return (Base.println)(Base.STDOUT,"I'm a vector")::Any 
> > 
> >       goto 2 
> > 
> >       0:  # line 5: 
> > 
> >       unless 2 === 2::Bool goto 1 # line 6: 
> > 
> >       return (Base.println)(Base.STDOUT,"I'm a matrix")::Any 
> > 
> >       goto 2 
> > 
> >       1: 
> > 
> >       return 
> > 
> >       2: 
> > 
> >   end::Any 
> > 
> > 
> > 
> > while all other methods do eliminate branching: 
> > 
> > 
> > Body: 
> > 
> >   begin  # none, line 2: 
> > 
> >       (Base.println)(Base.STDOUT,"I'm an array")::Any # line 3: 
> > 
> >       return (Base.println)(Base.STDOUT,"I'm a matrix")::Any 
> > 
> >   end::Any 
> > 
> > 
> > 
> > On Tuesday, September 29, 2015 at 8:57:10 PM UTC-4, Stefan Karpinski 
> wrote: 
> >> 
> >> The branch on the first version will be eliminated. The second version 
> is 
> >> far more idiomatic, however. Consider that the second version is 
> trivially 
> >> extensible to more types while the first version cannot be extended at 
> all. 
> >> 
> >> On Tuesday, September 29, 2015, Matt <matth...@gmail.com 
> <javascript:>> 
> >> wrote: 
> >> 
> >>> I want to write a method that is very similar between two types, with 
> >>> slight divergences. I'd like to write it avoiding code duplication. 
> >>> 
> >>> To take a simple example, let's say that the two types are Vector and 
> >>> Matrix. The method must print "I'm an array" for the two types, and 
> then 
> >>> prints "I'm a vector"  if the object is a vector, "I'm a matrix" if 
> the 
> >>> object is a matrix. 
> >>> 
> >>> One way write this method is to use a "run time" dispatch 
> >>> 
> >>> function f{T, N}(x::Array{T, N}) 
> >>>     println("I'm an array") 
> >>>     if N == 1 
> >>>        println("I'm a vector") 
> >>>    elseif N == 2 
> >>>         println("I'm a matrix") 
> >>>     end 
> >>> end 
> >>> f2(rand(10, 10)) 
> >>> @code_warntype f2(rand(10, 10)) 
> >>> 
> >>> A way to dispatch at compile time is to define as many auxiliary 
> function 
> >>> as there are differing lines 
> >>> 
> >>> function _ansfunction(x::Vector) 
> >>>    println("I'm a vector") 
> >>> end 
> >>> function _ansfunction(x::Matrix) 
> >>>     println("I'm a matrix") 
> >>> end 
> >>> function f1(x) 
> >>>     println("I'm an array") 
> >>>     _ansfunction(x) 
> >>> end 
> >>> f1(rand(10, 10)) 
> >>> @code_warntype f1(rand(10, 10)) 
> >>> 
> >>> Another solution would be to iterate through two NTuples, where N is 
> the 
> >>> number of differing lines 
> >>> 
> >>> for (t, x) in ((:Vector, :(println("I'm a vector"))), 
> >>>                 (:Matrix, :(println("I'm a Matrix")))) 
> >>>     @eval begin 
> >>>         function f2(x::$t) 
> >>>             println("I'm an array") 
> >>>             $x 
> >>>         end 
> >>>     end 
> >>> end 
> >>> f2(rand(10, 10)) 
> >>> @code_warntype f2(rand(10, 10)) 
> >>> 
> >>> 
> >>> These two last solutions work, but I really prefer the syntax of first 
> >>> solution : it allows to write the differing lines exactly at the place 
> >>> they're needed, when they're needed. It really starts to mattes when 
> there 
> >>> are a few differing lines. Is there a syntax as clear as the first 
> >>> solution, but that "branch" at compile time? 
> >>> 
> >> 
>

Reply via email to