簡體   English   中英

朱莉婭語言中的泛型浮點類型?

[英]Generic Float type in Julia language?

我的問題很簡單,茱莉亞是否有通用的Float類型? 例如,對於Integer ,只需編寫Int ,在32位系統中它將轉換為Int32 ,在64位系統中將其轉換為Int64 對於Float ,請參見下面的示例函數:

function bb(n)
    b = Array{Float64}(n) 
    b[1] = 0.9999
    for i = 2:n
        @inbounds b[i] = b[i-1] * 0.9999
    end    
    println(b[n])
end

bb(10^3)
@time bb(10^3)
@time bb(10^8)

它給出了以下計時結果以及總的內存分配:

0.9048328935585562
0.9048328935585562
  0.000100 seconds (135 allocations: 15.750 KB)
2.4703e-320
  3.230642 seconds (14 allocations: 762.940 MB, 1.51% gc time)

現在,將第一行更改為b = Array{AbstractFloat}(n)並查看可笑的巨大時序和內存分配:

0.9048328935585562
0.9048328935585562
  0.003564 seconds (2.13 k allocations: 46.953 KB)
2.4703e-320
  351.068176 seconds (200.00 M allocations: 3.725 GB, 0.74% gc time)

沒有什么可以使用的,因為b = Array{Float}(n) ,我想出的唯一解決方案是這種非優雅的符號b = Array{typeof(1.0)}(n)

您與Abstract Float有關的問題與32位或64位無關。

Julia沒有與Int匹配的Float ,因為浮點文字始終為 Float64。
即在64位或32位系統上, typeof(1.0)==Float64 (對於Float32文字,請使用1.0f0

如果您真的想要一個,則需要將其定義為

@static if Sys.WORDSIZE == 64
    const Float = Float64
else
    const Float = Float32
end

但這似乎沒有用,因為它與任何內容都不對應。 即使在CPU中實現浮點數學運算(通常)是64位(即使在32位CPU上),也不會更接近硬件。

請參見: 此線程在Discourse Float類型上,例如Int type

在32位系統上使用Float32和在64位系統上使用Float64沒有優勢。 在任何地方使用Float32都有好處-如果您不需要精度-關鍵之一是將內存分配減半-這將使分配時間和進程間通信時間減半。

關於您的性能問題:

b = Array{AbstractFloat}(n)性能較差是因為您正在創建一個包含抽象類型的容器。 請參見性能提示:避免使用帶有抽象類型參數的容器這些操作很慢,因為它們基本上是指針數組-每次與元素進行交互時都需要取消對指針的引用。 這是因為已聲明此數組b可能包含許多不同類型的元素。 有些可能是Float16 ,有些可能是Float32 ,有些甚至可能是BigFloatArbFloat{221} 因此,包含抽象類型的容器使用起來很慢,因為它們是指針數組。

因此,編寫b = Array{typeof(1.0)}(n)與編寫b = Array{Float64}(n)完全等效。 因此,這顯然不能解決您的真正問題。

假設您的真正問題是要指定返回的類型,則應將其作為參數傳遞:

function bb(T, n)
    b = Array{T}(n) 
    b[1] = 0.9999
    for i = 2:n
        @inbounds b[i] = b[i-1] * 0.9999
    end    
    println(b[n])
end

bb(Float32, 100) )進行調用。 由於所有數學運算都是在Float64中進行的,因為它是使用Float64文字指定的,但是當您將其分配給數組時,將隱式調用convert(T,...)

另外,您可能要傳遞值,然后推斷類型:

function bb(n, b1::T)
    b = Array{T}(n) 
    b[1] = b1
    for i = 2:n
        @inbounds b[i] = b[i-1] * b1
    end    
    println(b[n])
end

呼叫: bb(100, 0.9999f0)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM