Просмотр пониженной версии кода Джулии, который не находится в функции - PullRequest
0 голосов
/ 08 мая 2018

Я читал этот вопрос о производительности с глобальными переменными и хотел посмотреть, как именно Юлия переводит этот код. Тогда я понял, что code_warntype здесь нельзя использовать обычным образом, так как код не находится в функции, и его обертывание в функции разрушит весь смысл упражнения.

Есть ли аналог или другая версия @code_warntype, которая будет принимать код Julia напрямую (например, в качестве имени файла или в виде простой строки) и показывать нам типизированную уменьшенную версию этого кода? Или, возможно, флаг командной строки, который выводит пониженный код? (Казалось, есть флаги для генерации кода LLVM или объектных файлов, но нет для вывода кода, который просто выводит и выводит тип.)

1 Ответ

0 голосов
/ 08 мая 2018

Вы всегда можете заключить рассматриваемый код в функцию и вызвать @code_warntype для этого.

Вот пример для связанного вопроса:

n=5000;
x=rand(n)
y=rand(n)
mn=ones(n)*1000;
function foo()
    for i in 1:n;
        for j in 1:n;
            c=abs(x[j]-y[i]);
            if(c<mn[i])
                mn[i]=c;
            end
        end
    end
end

julia> @code_warntype foo()
Variables:
  #temp#@_2::Any
  i::Any
  #temp#@_4::Any
  j::Any
  c::Any

Body:
  begin
      Core.SSAValue(0) = (1:Main.n)::Any
      #temp#@_2::Any = (Base.start)(Core.SSAValue(0))::Any
      3: 
      Core.SSAValue(1) = (Base.done)(Core.SSAValue(0), #temp#@_2::Any)::Any
      Core.SSAValue(2) = (Core.typeassert)(Core.SSAValue(1), Core.Bool)::Bool
      Core.SSAValue(3) = (Base.not_int)(Core.SSAValue(2))::Bool
      unless Core.SSAValue(3) goto 37
      Core.SSAValue(4) = (Base.next)(Core.SSAValue(0), #temp#@_2::Any)::Any
      i::Any = (Core.getfield)(Core.SSAValue(4), 1)::Any
      #temp#@_2::Any = (Core.getfield)(Core.SSAValue(4), 2)::Any
      #= line 2 =#
      Core.SSAValue(5) = (1:Main.n)::Any
      #temp#@_4::Any = (Base.start)(Core.SSAValue(5))::Any
      14: 
      Core.SSAValue(6) = (Base.done)(Core.SSAValue(5), #temp#@_4::Any)::Any
      Core.SSAValue(7) = (Core.typeassert)(Core.SSAValue(6), Core.Bool)::Bool
      Core.SSAValue(8) = (Base.not_int)(Core.SSAValue(7))::Bool
      unless Core.SSAValue(8) goto 35
      Core.SSAValue(9) = (Base.next)(Core.SSAValue(5), #temp#@_4::Any)::Any
      j::Any = (Core.getfield)(Core.SSAValue(9), 1)::Any
      #temp#@_4::Any = (Core.getfield)(Core.SSAValue(9), 2)::Any
      #= line 3 =#
      Core.SSAValue(10) = (Base.getindex)(Main.x, j::Any)::Any
      Core.SSAValue(11) = (Base.getindex)(Main.y, i::Any)::Any
      Core.SSAValue(12) = (Core.SSAValue(10) - Core.SSAValue(11))::Any
      c::Any = (Main.abs)(Core.SSAValue(12))::Any
      #= line 5 =#
      Core.SSAValue(14) = (Base.getindex)(Main.mn, i::Any)::Any
      Core.SSAValue(15) = (c::Any < Core.SSAValue(14))::Any
      unless Core.SSAValue(15) goto 33
      #= line 6 =#
      (Base.setindex!)(Main.mn, c::Any, i::Any)::Any
      33: 
      goto 14
      35: 
      goto 3
      37: 
      return
  end::Nothing

Сравните выше с

function foo()
    n=5000;
    x=rand(n)
    y=rand(n)
    mn=ones(n)*1000;
    for i in 1:n;
        for j in 1:n;
            c=abs(x[j]-y[i]);
            if(c<mn[i])
                mn[i]=c;
            end
        end
    end
end

julia> @code_warntype foo()
Variables:
  n<optimized out>
  x<optimized out>
  y<optimized out>
  mn::Array{Float64,1}
  #temp#@_6::Int64
  i<optimized out>
  #temp#@_8::Int64
  j<optimized out>
  c<optimized out>
  #temp#@_13::Bool
  #temp#@_16::Bool

Body:
  begin
      #= line 3 =#
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand 224
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand 236
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand 235
      # meta: location boot.jl Type 397
      # meta: location boot.jl Type 389
      # meta: location boot.jl Type 380
      Core.SSAValue(46) = $(Expr(:foreigncall, :(:jl_alloc_array_1d), Array{Float64,1}, svec(Any, Int64), :(:ccall), 2, Array{Float64,1}, 5000, 5000))
      # meta: pop locations (3)
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand! 214
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/RNGs.jl rand! 447
      # meta: location array.jl length 137
      Core.SSAValue(53) = (Base.arraylen)(Core.SSAValue(46))::Int64
      # meta: pop location
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/RNGs.jl _rand! 440
      # meta: location int.jl * 54
      Core.SSAValue(66) = (Base.mul_int)(8, Core.SSAValue(53))::Int64
      # meta: pop location
      # meta: location array.jl length 137
      Core.SSAValue(67) = (Base.arraylen)(Core.SSAValue(46))::Int64
      # meta: pop location
      # meta: location int.jl * 54
      Core.SSAValue(68) = (Base.mul_int)(8, Core.SSAValue(67))::Int64
      # meta: pop location
      # meta: location int.jl <= 419
      Core.SSAValue(69) = (Base.sle_int)(Core.SSAValue(66), Core.SSAValue(68))::Bool
      # meta: pop location
      unless Core.SSAValue(69) goto 31
      #temp#@_13::Bool = true
      goto 33
      31: 
      #temp#@_13::Bool = false
      33: 
      unless #temp#@_13::Bool goto 36
      goto 41
      36: 
      # meta: location boot.jl Type 281
      Core.SSAValue(71) = $(Expr(:new, :(Core.AssertionError), "sizeof(Float64) * n64 <= sizeof(T) * length(A) && isbits(T)"))
      # meta: pop location
      (Base.throw)(Core.SSAValue(71))::Union{}
      41: 
      #= line 441 =#
      # meta: location gcutils.jl
      #= line 81 =#
      Core.SSAValue(61) = $(Expr(:gc_preserve_begin, Core.SSAValue(46)))
      #= line 82 =#
      # meta: location abstractarray.jl pointer 911
      # meta: location pointer.jl unsafe_convert 65
      Core.SSAValue(74) = $(Expr(:foreigncall, :(:jl_array_ptr), Ptr{Float64}, svec(Any), :(:ccall), 1, Core.SSAValue(46)))
      # meta: pop locations (2)
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/RNGs.jl Type 365
      Core.SSAValue(79) = $(Expr(:new, Random.UnsafeView{Float64}, Core.SSAValue(74), Core.SSAValue(53)))
      # meta: pop location
      $(Expr(:invoke, MethodInstance for rand!(::Random.MersenneTwister, ::Random.UnsafeView{Float64}, ::Random.SamplerTrivial{Random.CloseOpen01{Float64},Float64}), :(Random.rand!), :(Random.GLOBAL_RNG), Core.SSAValue(79), :($(QuoteNode(Random.SamplerTrivial{Random.CloseOpen01{Float64},Float64}(Random.CloseOpen01{Float64}()))))))::Random.UnsafeView{Float64}
      #= line 83 =#
      $(Expr(:gc_preserve_end, Core.SSAValue(61)))
      # meta: pop locations (7)
      #= line 4 =#
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand 224
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand 236
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand 235
      # meta: location boot.jl Type 397
      # meta: location boot.jl Type 389
      # meta: location boot.jl Type 380
      Core.SSAValue(109) = $(Expr(:foreigncall, :(:jl_alloc_array_1d), Array{Float64,1}, svec(Any, Int64), :(:ccall), 2, Array{Float64,1}, 5000, 5000))
      # meta: pop locations (3)
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/Random.jl rand! 214
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/RNGs.jl rand! 447
      # meta: location array.jl length 137
      Core.SSAValue(116) = (Base.arraylen)(Core.SSAValue(109))::Int64
      # meta: pop location
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/RNGs.jl _rand! 440
      # meta: location int.jl * 54
      Core.SSAValue(129) = (Base.mul_int)(8, Core.SSAValue(116))::Int64
      # meta: pop location
      # meta: location array.jl length 137
      Core.SSAValue(130) = (Base.arraylen)(Core.SSAValue(109))::Int64
      # meta: pop location
      # meta: location int.jl * 54
      Core.SSAValue(131) = (Base.mul_int)(8, Core.SSAValue(130))::Int64
      # meta: pop location
      # meta: location int.jl <= 419
      Core.SSAValue(132) = (Base.sle_int)(Core.SSAValue(129), Core.SSAValue(131))::Bool
      # meta: pop location
      unless Core.SSAValue(132) goto 88
      #temp#@_16::Bool = true
      goto 90
      88: 
      #temp#@_16::Bool = false
      90: 
      unless #temp#@_16::Bool goto 93
      goto 98
      93: 
      # meta: location boot.jl Type 281
      Core.SSAValue(134) = $(Expr(:new, :(Core.AssertionError), "sizeof(Float64) * n64 <= sizeof(T) * length(A) && isbits(T)"))
      # meta: pop location
      (Base.throw)(Core.SSAValue(134))::Union{}
      98: 
      #= line 441 =#
      # meta: location gcutils.jl
      #= line 81 =#
      Core.SSAValue(124) = $(Expr(:gc_preserve_begin, Core.SSAValue(109)))
      #= line 82 =#
      # meta: location abstractarray.jl pointer 911
      # meta: location pointer.jl unsafe_convert 65
      Core.SSAValue(137) = $(Expr(:foreigncall, :(:jl_array_ptr), Ptr{Float64}, svec(Any), :(:ccall), 1, Core.SSAValue(109)))
      # meta: pop locations (2)
      # meta: location /buildworker/worker/package_linux64/build/usr/share/julia/site/v0.7/Random/src/RNGs.jl Type 365
      Core.SSAValue(142) = $(Expr(:new, Random.UnsafeView{Float64}, Core.SSAValue(137), Core.SSAValue(116)))
      # meta: pop location
      $(Expr(:invoke, MethodInstance for rand!(::Random.MersenneTwister, ::Random.UnsafeView{Float64}, ::Random.SamplerTrivial{Random.CloseOpen01{Float64},Float64}), :(Random.rand!), :(Random.GLOBAL_RNG), Core.SSAValue(142), :($(QuoteNode(Random.SamplerTrivial{Random.CloseOpen01{Float64},Float64}(Random.CloseOpen01{Float64}()))))))::Random.UnsafeView{Float64}
      #= line 83 =#
      $(Expr(:gc_preserve_end, Core.SSAValue(124)))
      # meta: pop locations (7)
      #= line 5 =#
      # meta: location array.jl ones 398
      # meta: location array.jl ones 396
      # meta: location array.jl ones 395
      # meta: location boot.jl Type 389
      # meta: location boot.jl Type 380
      Core.SSAValue(170) = $(Expr(:foreigncall, :(:jl_alloc_array_1d), Array{Float64,1}, svec(Any, Int64), :(:ccall), 2, Array{Float64,1}, 5000, 5000))
      # meta: pop locations (2)
      Core.SSAValue(151) = $(Expr(:invoke, MethodInstance for fill!(::Array{Float64,1}, ::Float64), :(Base.fill!), Core.SSAValue(170), 1.0))::Array{Float64,1}
      # meta: pop locations (3)
      mn::Array{Float64,1} = $(Expr(:invoke, MethodInstance for *(::Array{Float64,1}, ::Int64), :(Main.:*), Core.SSAValue(151), 1000))::Array{Float64,1}
      #= line 6 =#
      #temp#@_6::Int64 = 1
      128: 
      # meta: location range.jl done 457
      # meta: location int.jl + 53
      Core.SSAValue(197) = (Base.add_int)(5000, 1)::Int64
      # meta: pop location
      # meta: location promotion.jl == 433
      Core.SSAValue(198) = (#temp#@_6::Int64 === Core.SSAValue(197))::Bool
      # meta: pop locations (2)
      Core.SSAValue(4) = (Base.not_int)(Core.SSAValue(198))::Bool
      unless Core.SSAValue(4) goto 193
      # meta: location range.jl next 456
      # meta: location int.jl + 53
      Core.SSAValue(203) = (Base.add_int)(#temp#@_6::Int64, 1)::Int64
      # meta: pop location
      Core.SSAValue(246) = #temp#@_6::Int64
      # meta: pop location
      #temp#@_6::Int64 = Core.SSAValue(203)
      #= line 6 =#
      #temp#@_8::Int64 = 1
      147: 
      # meta: location range.jl done 457
      # meta: location int.jl + 53
      Core.SSAValue(229) = (Base.add_int)(5000, 1)::Int64
      # meta: pop location
      # meta: location promotion.jl == 433
      Core.SSAValue(230) = (#temp#@_8::Int64 === Core.SSAValue(229))::Bool
      # meta: pop locations (2)
      Core.SSAValue(9) = (Base.not_int)(Core.SSAValue(230))::Bool
      unless Core.SSAValue(9) goto 191
      # meta: location range.jl next 456
      # meta: location int.jl + 53
      Core.SSAValue(235) = (Base.add_int)(#temp#@_8::Int64, 1)::Int64
      # meta: pop location
      Core.SSAValue(245) = #temp#@_8::Int64
      # meta: pop location
      #temp#@_8::Int64 = Core.SSAValue(235)
      #= line 7 =#
      # meta: location array.jl getindex 661
      Core.SSAValue(236) = (Base.arrayref)(true, Core.SSAValue(46), Core.SSAValue(245))::Float64
      # meta: pop location
      # meta: location array.jl getindex 661
      Core.SSAValue(237) = (Base.arrayref)(true, Core.SSAValue(109), Core.SSAValue(246))::Float64
      # meta: pop location
      # meta: location float.jl - 395
      Core.SSAValue(238) = (Base.sub_float)(Core.SSAValue(236), Core.SSAValue(237))::Float64
      # meta: pop location
      # meta: location float.jl abs 517
      Core.SSAValue(239) = (Base.abs_float)(Core.SSAValue(238))::Float64
      # meta: pop location
      #= line 9 =#
      # meta: location array.jl getindex 661
      Core.SSAValue(240) = (Base.arrayref)(true, mn::Array{Float64,1}, Core.SSAValue(246))::Float64
      # meta: pop location
      # meta: location float.jl < 450
      Core.SSAValue(241) = (Base.lt_float)(Core.SSAValue(239), Core.SSAValue(240))::Bool
      # meta: pop location
      unless Core.SSAValue(241) goto 189
      #= line 10 =#
      # meta: location array.jl setindex! 699
      (Base.arrayset)(true, mn::Array{Float64,1}, Core.SSAValue(239), Core.SSAValue(246))::Array{Float64,1}
      # meta: pop location
      189: 
      goto 147
      191: 
      goto 128
      193: 
      return
  end::Nothing
...