Julia 中,如果類型被省略,則值可以是任意類型。添加類型會顯著提高性能和系統(tǒng)穩(wěn)定性。
Julia 類型系統(tǒng)的特性是,具體類型不能作為具體類型的子類型,所有的具體類型都是最終的,它們可以擁有抽象類型作為父類型。其它高級特性有:
Julia 的類型系統(tǒng)的設(shè)計旨在有效及具表現(xiàn)力,既清楚直觀又不夸張。許多 Julia 程序員可能永遠不會覺得有必要去明確地指出類型。然而某些程序會因聲明類型變得更清晰,更簡單,更迅速及健壯。
::
運算符可以用來在程序中給表達式和變量附加類型注釋。這樣做有兩個理由:
::
運算符放在表示值的表達式之后時讀作“前者是后者的實例”,它用來斷言左側(cè)表達式是否為右側(cè)表達式的實例。如果右側(cè)是具體類型,此類型應(yīng)該是左側(cè)的實例。如果右側(cè)是抽象類型,左側(cè)應(yīng)是一個具體類型的實例的值,該具體類型是這個抽象類型的子類型。如果類型斷言為假,將拋出異常,否則,返回左值:
julia> (1+2)::FloatingPoint
ERROR: type: typeassert: expected FloatingPoint, got Int64
julia> (1+2)::Int
3
可以在任何表達式的所在位置做類型斷言。 ::
最常見的用法是作為一個在函數(shù)/方法簽名中的斷言,例如 f(x::Int8) = ...
(查看方法)。
::
運算符跟在表達式上下文中的變量名后時,它聲明變量應(yīng)該是某個類型,有點兒類似于 C 等靜態(tài)語言中的類型聲明。賦給這個變量的值會被 convert
函數(shù)轉(zhuǎn)換為所聲明的類型:
julia> function foo()
x::Int8 = 1000
x
end
foo (generic function with 1 method)
julia> foo()
-24
julia> typeof(ans)
Int8
這個特性用于避免性能陷阱,即給一個變量賦值時意外更改了類型。
“聲明”僅發(fā)生在特定的上下文中:
x::Int8 # a variable by itself
local x::Int8 # in a local declaration
x::Int8 = 10 # as the left-hand side of an assignment
并適用于整個當(dāng)前范圍,甚至在聲明之前。目前,聲明類型不能用于全局范圍,例如在 REPL 中就不可以,因為 Julia 還沒有定型的全局變量。需要注意的是在函數(shù)返回語句中,上述的前兩個表達式計算值,還有就是 ::
是一個類型的斷言不是一個聲明。
抽象類型不能被實例化,它組織了類型等級關(guān)系,方便程序員編程。如,編程時可針對任意整數(shù)類型,而不需指明是哪種具體的整數(shù)類型。
使用 abstract
關(guān)鍵字聲明抽象類型:
abstract ?name?
abstract ?name? <: ?supertype?
abstract
關(guān)鍵字引入了新的抽象類型,類型名為 ?name?
。類型名后可跟 <:
及已存在的類型,表明新聲明的抽象類型是這個“父”類型的子類型。
如果沒有指明父類型,則父類型默認(rèn)為 Any
——所有對象和類型都是這個抽象類型的子類型。在類型理論中,Any
位于類型圖的頂峰,被稱為“頂”。Julia 也有預(yù)定義的抽象“底”類型,它位于類型圖的最底處,被稱為 None
。None
與 Any
對立:任何對象都不是 None
的實例,所有的類型都是 None
的父類型。
下面是構(gòu)造 Julia 數(shù)值體系的抽象類型子集的具體例子:
abstract Number end
abstract Real <: Number
abstract AbstractFloat <: Real
abstract Integer <: Real
abstract Signed <: Integer
abstract Unsigned <: Integer
<:
運算符意思為“前者是后者的子類型”,它聲明右側(cè)是左側(cè)新聲明類型的直接父類型。也可以用來判斷左側(cè)是不是右側(cè)的子類型:
julia> Integer <: Number
true
julia> Integer <: FloatingPoint
false
抽象類型的一個重要用途是為具體的類型提供默認(rèn)實現(xiàn)。舉個簡單的例子:
function myplus(x, y)
x + y
endof
第一點需要注意的是, 上面的參數(shù)聲明等效于 x::Any
和 y::Any
. 當(dāng)這個函數(shù)被調(diào)用時, 例如 myplus(2, 5)
, Julia 會首先查找參數(shù)類型匹配的 myplus
函數(shù). (關(guān)于多重分派的詳細信息請參考下文.) 如果沒有找到比上面的函數(shù)更相關(guān)的函數(shù), Julia 根據(jù)上面的通用函數(shù)定義并編譯一個 myplus
具體函數(shù), 其參數(shù)為兩個 Int 型變量, 也就是說,
Julia 會定義并編譯:
function myplus(x::Int, y::Int)
x + y
end
最后, 調(diào)用這個具體的函數(shù)。
因此, 程序員可以利用抽象類型編寫通用的函數(shù),然后這個通用函數(shù)可以被許多具體的類型組合調(diào)用。也正是由于多重分派,程序員可以精確的控制是調(diào)用更具體的還是通用的函數(shù)。
需要注意的一點是, 編寫面向抽象類型的函數(shù)并不會帶來性能上的損失,因為每次調(diào)用函數(shù)時,根據(jù)不同的參數(shù)組合,函數(shù)總是要重新編譯的。(然而, 如果參數(shù)類型為包含抽象類型的容器是, 會有性能方面的問題;參見下面的關(guān)于性能的提示。)
位類型是具體類型,它的數(shù)據(jù)是由位構(gòu)成的。整數(shù)和浮點數(shù)都是位類型。標(biāo)準(zhǔn)的位類型是用 Julia 語言本身定義的:
bitstype 16 Float16 <: FloatingPoint
bitstype 32 Float32 <: FloatingPoint
bitstype 64 Float64 <: FloatingPoint
bitstype 8 Bool <: Integer
bitstype 32 Char <: Integer
bitstype 8 Int8 <: Signed
bitstype 8 Uint8 <: Unsigned
bitstype 16 Int16 <: Signed
bitstype 16 Uint16 <: Unsigned
bitstype 32 Int32 <: Signed
bitstype 32 Uint32 <: Unsigned
bitstype 64 Int64 <: Signed
bitstype 64 Uint64 <: Unsigned
bitstype 128 Int128 <: Signed
bitstype 128 Uint128 <: Unsigned
聲明位類型的通用語法是:
bitstype ?bits? ?name?
bitstype ?bits? ?name? <: ?supertype?
?bits?
表明類型需要多少空間來存儲,?name?
為新類型的名字。目前,位類型的聲明的位數(shù)只支持 8 的倍數(shù),因此布爾類型也是 8 位的。
Bool
, Int8
及 Uint8
類型的聲明是完全相同的,都占用了 8 位內(nèi)存,但它們是互相獨立的。
復(fù)合類型也被稱為記錄、結(jié)構(gòu)、或者對象。復(fù)合類型是變量名域的集合。它是 Julia 中最常用的自定義類型。在 Julia 中,所有的值都是對象,但函數(shù)并不與它們所操作的對象綁定。Julia 重載時,根據(jù)函數(shù) 所有參數(shù)的類型,而不僅僅是第一個參數(shù)的類型,來選取調(diào)用哪個方法(詳見 :方法 )。
使用 type
關(guān)鍵字來定義復(fù)合類型:
julia> type Foo
bar
baz::Int
qux::Float64
end
構(gòu)建復(fù)合類型 Foo
的對象:
julia> foo = Foo("Hello, world.", 23, 1.5)
Foo("Hello, world.",23,1.5)
julia> typeof(foo)
Foo (constructor with 2 methods)
當(dāng)一個類型像函數(shù)一樣被調(diào)用時,它可以被叫做類型構(gòu)造函數(shù)(constructor)。每個類型有兩種構(gòu)造函數(shù)是自動被生成的(它們被叫做默認(rèn)構(gòu)造函數(shù))。第一種是當(dāng)傳給構(gòu)造函數(shù)的參數(shù)和這個類型的字段類型不一一匹配時,構(gòu)造函數(shù)會把它的參數(shù)傳給 convert
函數(shù),并且轉(zhuǎn)換到這個類型相應(yīng)的字段類型。第二種是當(dāng)傳給構(gòu)造函數(shù)的每個參數(shù)和這個類型的字段類型都一一相同時,構(gòu)造函數(shù)直接生成類型。要自動生成兩種默認(rèn)構(gòu)造函數(shù)的原因是:為了防止用戶在聲明別的新變量的時候不小心把構(gòu)造函數(shù)給覆蓋掉。
由于沒有約束 bar
的類型,它可以被賦任意值;但是 baz
必須能被轉(zhuǎn)換為 Int
:
julia> Foo((), 23.5, 1)
ERROR: InexactError()
in Foo at no file
你可以用 names
這個函數(shù)來獲取類型的所有字段。
julia> names(foo)
3-element Array{Symbol,1}:
:bar
:baz
:qux
獲取復(fù)合對象域的值:
julia> foo.bar
"Hello, world."
julia> foo.baz
23
julia> foo.qux
1.5
修改復(fù)合對象域的值:
julia> foo.qux = 2
2.0
julia> foo.bar = 1//2
1//2
沒有域的復(fù)合類型是單態(tài)類型,這種類型只能有一個實例:
type NoFields
end
julia> is(NoFields(), NoFields())
true
is
函數(shù)驗證 NoFields
的“兩個”實例是否為同一個。有關(guān)單態(tài)類型,后面會詳細講。
有關(guān)復(fù)合類型如何實例化,需要 參數(shù)化類型和方法這兩個背景知識。將在構(gòu)造函數(shù)中詳細介紹構(gòu)造實例。
可以使用關(guān)鍵詞 immutable
替代 type
來定義 不可變 復(fù)合類型:
immutable Complex
real::Float64
imag::Float64
end
這種類型和其他復(fù)合類型類似,除了它們的實例不能被更改。不可變復(fù)合類型具有以下幾種優(yōu)勢:
Complex
例子里的類型就被有效地封裝到數(shù)組里,而且有些時候編譯器能夠避免完整地分配不可變對象。一個不可變對象可以包含可變對象,比如數(shù)組,域。那些被包含的可變對象仍然保持可變;只有不可變對象自己的域不能變得指向別的對象。
理解不可變復(fù)合變量的一個有用的辦法是每個實例都是和特定域的值相關(guān)聯(lián)的 - 這些域的值就能告訴你關(guān)于這個對象的一切。相反地,一個可變的對象就如同一個小的容器可能包含了各種各樣的值,所以它不能從它的域的值確定出這個對象。在決定是否把一個類型定義為不變的時候,先問問是否兩個實例包含相同的域的值就被認(rèn)為是相同,或者它們會獨立地改變。如果它們被認(rèn)為是相同的,那么這個類型就該被定義成不可變的。
再次強調(diào)下, Julia 中不可變類型有兩個重要的特性:
對于有著 C/C++ 背景的讀者, 需要仔細想下為什么這兩個特性是息息相關(guān)的。設(shè)想下,如果這兩個特性是分開的,也就是說,如果數(shù)據(jù)在傳遞時是拷貝的, 然而數(shù)據(jù)內(nèi)部的變量可以被改變, 那么將很難界定某段代碼的實際作用。舉個例子,假設(shè) x
是某個函數(shù)的參數(shù), 同時假設(shè)函數(shù)改變了參數(shù)中的一個域:x.isprocessed = true
。根據(jù) x
是值傳遞或者引用傳遞, 在調(diào)用完函數(shù)是, 原來 x
的值有可能沒有改變,
也有可能改變. 為了防止出現(xiàn)這種不確定效應(yīng), Julia 限定如果參數(shù)是值傳遞, 其內(nèi)部域的值不可改變。
以上的三種類型是緊密相關(guān)的。它們有相同的特性:
正因有共有的特性,這些類型內(nèi)在地表達為同一種概念的實例,DataType
,是以下類型之一:
julia> typeof(Real)
DataType
julia> typeof(Int)
DataType
DataType
既可以抽象也可以具體。如果是具體的,它會擁有既定的大小,存儲安排和(可選的)名域。所以一個位類型是一個大小非零的 DataType
,但沒有名域。一個復(fù)合類型是一個可能擁有名域也可以為空集(大小為零)的 DataType
。
在這個系統(tǒng)里的每一個具體的值都是某個 DataType
的實例,或者一個多元組。
多元組的類型是類型的多元組:
julia> typeof((1,"foo",2.5))
(Int64,ASCIIString,Float64)
類型多元組可以在任何需要類型的地方使用:
julia> (1,"foo",2.5) :: (Int64,String,Any)
(1,"foo",2.5)
julia> (1,"foo",2.5) :: (Int64,String,Float32)
ERROR: type: typeassert: expected (Int64,String,Float32), got (Int64,ASCIIString,Float64)
如果類型多元組中有非類型出現(xiàn),會報錯:
julia> (1,"foo",2.5) :: (Int64,String,3)
ERROR: type: typeassert: expected Type{T<:Top}, got (DataType,DataType,Int64)
注意,空多元組 ()
的類型是其本身:
julia> typeof(())
()
多元組類型是關(guān)于它的組成類型是協(xié)變的,一個多元組是另一個多元組的子類型意味著對應(yīng)的第一個多元組的各元素的類型是第二個多元組對應(yīng)元素類型的子類型。比如:
julia> (Int,String) <: (Real,Any)
true
julia> (Int,String) <: (Real,Real)
false
julia> (Int,String) <: (Real,)
false
直觀地看,這就像一個函數(shù)的各個參數(shù)的類型必須是函數(shù)簽名的子類型(當(dāng)簽名匹配的時候)。
類型共用體是特殊的抽象類型,使用 Union
函數(shù)來聲明:
julia> IntOrString = Union(Int,String)
Union(String,Int64)
julia> 1 :: IntOrString
1
julia> "Hello!" :: IntOrString
"Hello!"
julia> 1.0 :: IntOrString
ERROR: type: typeassert: expected Union(String,Int64), got Float64
不含任何類型的類型共用體,是“底”類型 None
:
julia> Union()
None
抽象類型 None
是所有其它類型的子類型,且沒有實例。零參的 Union
調(diào)用,將返回?zé)o實例的類型 None
。
Julia 的類型系統(tǒng)支持參數(shù)化:類型可以引入?yún)?shù),這樣類型聲明為每種可能的參數(shù)組合聲明一個新類型。
所有被聲明的類型(DataType
的變體)都可以使用同樣的語法來參數(shù)化。我們將按照如下順序來討論:參數(shù)化符合類型、參數(shù)化抽象類型、參數(shù)化位類型。
abstract Pointy{T}
type Point{T} <: Pointy{T}
x::T
y::T
end
類型參數(shù)跟在類型名后,用花括號括起來:
type Point{T}
x::T
y::T
end
這個聲明定義了新參數(shù)化類型 Point{T}
,它有兩個 T
類型的“坐標(biāo)軸”。參數(shù)化類型可以是任何類型(也可以是整數(shù),此例中我們用的是類型)。具體類型 Point{Float64}
等價于將 Point
中的 T
替換為 Float64
后的類型。上例實際上聲明了許多種類型:Point{Float64}
, Point{String}
, Point{Int64}
等等,因此,現(xiàn)在每個都是可以使用的具體類型:
julia> Point{Float64}
Point{Float64} (constructor with 1 method)
julia> Point{String}
Point{String} (constructor with 1 method)
Point
本身也是個有效的類型對象:
julia> Point
Point{T} (constructor with 1 method)
Point
在這兒是一個抽象類型,它包含所有如 Point{Float64}
, Point{String}
之類的具體實例:
julia> Point{Float64} <: Point
true
julia> Point{String} <: Point
true
其它類型則不是其子類型:
julia> Float64 <: Point
false
julia> String <: Point
false
Point
不同 T
值所聲明的具體類型之間,不能互相作為子類型:
julia> Point{Float64} <: Point{Int64}
false
julia> Point{Float64} <: Point{Real}
false
這一點非常重要:
雖然 Float64 <: Real
,但 Point{Float64} <: Point{Real}
不成立!
換句話說,Julia 的類型參數(shù)是 不相關(guān) 的。盡管 Point{Float64}
的實例按照概念來說,應(yīng)該是 Point{Real}
的實例,但兩者在內(nèi)存中的表示上有區(qū)別:
Point{Float64}
的實例可以簡便、有效地表示 64 位數(shù)對兒Point{Real}
的實例可以表示任意 Real
實例的數(shù)對兒。由于 Real
的實例可以為任意大小、任意結(jié)構(gòu),因此 Point{Real}
實際上表示指向 Real
對象的指針對兒上述區(qū)別在數(shù)組中更明顯: Array{Float64}
可以在一塊連續(xù)內(nèi)存中存儲 64 位浮點數(shù),而 Array{Real}
則保存指向每個 Real
對象的指針數(shù)組。而每個 Real
對象的大小,可能比 64 位浮點數(shù)的大。
構(gòu)造函數(shù)中將介紹如何給復(fù)合類型自定義構(gòu)造方法,但如果沒有特殊構(gòu)造聲明時,默認(rèn)有兩種構(gòu)造新復(fù)合對象的方法:一種是明確指明構(gòu)造方法的類型參數(shù);另一種是由對象構(gòu)造方法的參數(shù)來隱含類型參數(shù)。
指明構(gòu)造方法的類型參數(shù):
julia> Point{Float64}(1.0,2.0)
Point{Float64}(1.0,2.0)
julia> typeof(ans)
Point{Float64} (constructor with 1 method)
參數(shù)個數(shù)應(yīng)與構(gòu)造函數(shù)相匹配:
julia> Point{Float64}(1.0)
ERROR: no method Point{Float64}(Float64)
julia> Point{Float64}(1.0,2.0,3.0)
ERROR: no method Point{Float64}(Float64, Float64, Float64)
對于帶有類型參數(shù)的類型,因為重載構(gòu)造函數(shù)是不可能的,所以只有一種默認(rèn)構(gòu)造函數(shù)被自動生成——這個構(gòu)造函數(shù)接受任何參數(shù)并且把們轉(zhuǎn)換成對應(yīng)的字段類型并賦值
大多數(shù)情況下不需要提供 Point
對象的類型,它可由參數(shù)類型來提供信息。因此,可以不提供 T
的值:
julia> Point(1.0,2.0)
Point{Float64}(1.0,2.0)
julia> typeof(ans)
Point{Float64} (constructor with 1 method)
julia> Point(1,2)
Point{Int64}(1,2)
julia> typeof(ans)
Point{Int64} (constructor with 1 method)
上例中,Point
的兩個參數(shù)類型相同,因此 T
可以省略。但當(dāng)參數(shù)類型不同時,會報錯:
julia> Point(1,2.5)
ERROR: `Point{T}` has no method matching Point{T}(::Int64, ::Float64)
這種情況其實也可以處理,詳見構(gòu)造函數(shù)。
類似地,參數(shù)化抽象類型聲明一個抽象類型的集合:
abstract Pointy{T}
對每個類型或整數(shù)值 T
,Pointy{T}
都是一個不同的抽象類型。Pointy
的每個實例都是它的子類型:
julia> Pointy{Int64} <: Pointy
true
julia> Pointy{1} <: Pointy
true
參數(shù)化抽象類型也是不相關(guān)的:
julia> Pointy{Float64} <: Pointy{Real}
false
julia> Pointy{Real} <: Pointy{Float64}
false
可以如下聲明 Point{T}
是 Pointy{T}
的子類型:
type Point{T} <: Pointy{T}
x::T
y::T
end
對每個 T
,都有 Point{T}
是 Pointy{T}
的子類型:
julia> Point{Float64} <: Pointy{Float64}
true
julia> Point{Real} <: Pointy{Real}
true
julia> Point{String} <: Pointy{String}
true
它們?nèi)匀皇遣幌嚓P(guān)的:
julia> Point{Float64} <: Pointy{Real}
false
參數(shù)化抽象類型 Pointy
有什么用呢?假設(shè)我們要構(gòu)造一個坐標(biāo)點的實現(xiàn),點都在對角線 x = y 上,因此我們只需要一個坐標(biāo)軸:
type DiagPoint{T} <: Pointy{T}
x::T
end
Point{Float64}
和 DiagPoint{Float64}
都是 Pointy{Float64}
抽象類型的實現(xiàn),這對其它可選類型 T
也一樣。 Pointy
可以作為它的子類型的公共接口。有關(guān)方法和重載,詳見下一節(jié) :ref:man-methods
。
有時需要對 T
的范圍做限制:
abstract Pointy{T<:Real}
此時, T
只能是 Real
的子類型:
julia> Pointy{Float64}
Pointy{Float64}
julia> Pointy{Real}
Pointy{Real}
julia> Pointy{String}
ERROR: type: Pointy: in T, expected T<:Real, got Type{String}
julia> Pointy{1}
ERROR: type: Pointy: in T, expected T<:Real, got Int64
參數(shù)化復(fù)合類型的類型參數(shù),也可以同樣被限制:
type Point{T<:Real} <: Pointy{T}
x::T
y::T
end
下面是 Julia 的 Rational
的 immutable 類型是如何定義的,這個類型表示分?jǐn)?shù):
immutable Rational{T<:Integer} <: Real
num::T
den::T
end
單態(tài)類型是一種特殊的抽象參數(shù)化類型。對每個類型 T
,抽象類型“單態(tài)” Type{T}
的實例為對象 T
。來看些例子:
julia> isa(Float64, Type{Float64})
true
julia> isa(Real, Type{Float64})
false
julia> isa(Real, Type{Real})
true
julia> isa(Float64, Type{Real})
false
換句話說,僅當(dāng) A
和 B
是同一個對象,且此對象是類型時,isa(A,Type{B})
才返回真。沒有參數(shù)時,Type
僅是抽象類型,所有的類型都是它的實例,包括單態(tài)類型:
julia> isa(Type{Float64},Type)
true
julia> isa(Float64,Type)
true
julia> isa(Real,Type)
true
只有對象是類型時,才是 Type
的實例:
julia> isa(1,Type)
false
julia> isa("foo",Type)
false
Julia 中只有類型對象才有單態(tài)類型。
可以參數(shù)化地聲明位類型。例如,Julia 中指針被定義為位類型:
# 32-bit system:
bitstype 32 Ptr{T}
# 64-bit system:
bitstype 64 Ptr{T}
這兒的參數(shù)類型 T
不是用來做類型定義,而是個抽象標(biāo)簽,它定義了一組結(jié)構(gòu)相同的類型,這些類型僅能由類型參數(shù)來區(qū)分。盡管 Ptr{Float64}
和 Ptr{Int64}
的表示是一樣的,它們是不同的類型。所有的特定指針類型,都是 Ptr
類型的子類型:
julia> Ptr{Float64} <: Ptr
true
julia> Ptr{Int64} <: Ptr
true
Julia 提供 typealias
機制來實現(xiàn)類型別名。如,Uint
是 Uint32
或 Uint64
的類型別名,這取決于系統(tǒng)的指針大?。?/p>
# 32-bit system:
julia> Uint
Uint32
# 64-bit system:
julia> Uint
Uint64
它是通過 base/boot.jl
中的代碼實現(xiàn)的:
if is(Int,Int64)
typealias Uint Uint64
else
typealias Uint Uint32
end
對參數(shù)化類型,typealias
提供了簡單的參數(shù)化類型名。Julia 的數(shù)組類型為 Array{T,n}
,其中 T
是元素類型, n
是數(shù)組維度的數(shù)值。為簡單起見,Array{Float64}
可以只指明元素類型而不需指明維度:
julia> Array{Float64,1} <: Array{Float64} <: Array
true
``Vector`` 和 ``Matrix`` 對象是如下定義的:
typealias Vector{T} Array{T,1}
typealias Matrix{T} Array{T,2}
Julia 中,類型本身也是對象,可以對其使用普通的函數(shù)。如 <:
運算符,可以判斷左側(cè)是否是右側(cè)的子類型。
isa
函數(shù)檢測對象是否屬于某個指定的類型:
julia> isa(1,Int)
true
julia> isa(1,FloatingPoint)
false
typeof
函數(shù)返回參數(shù)的類型。類型也是對象,因此它也有類型:
julia> typeof(Rational)
DataType
julia> typeof(Union(Real,Float64,Rational))
DataType
julia> typeof((Rational,None))
(DataType,UnionType)
類型的類型是什么?它們的類型是 DataType
:
julia> typeof(DataType)
DataType
julia> typeof(UnionType)
DataType
讀者也許會注意到,DataType
類似于空多元組(詳見上文 )。因此,遞歸使用 ()
和 DataType
所組成的多元組的類型,是該類型本身:
julia> typeof(())
()
julia> typeof(DataType)
DataType
julia> typeof(((),))
((),)
julia> typeof((DataType,))
(DataType,)
julia> typeof(((),DataType))
((),DataType)
super
可以指明一些類型的父類型。只有聲明的類型(DataType
)才有父類型:
julia> super(Float64)
FloatingPoint
julia> super(Number)
Any
julia> super(String)
Any
julia> super(Any)
Any
對其它類型對象(或非類型對象)使用 super
,會引發(fā) “no method” 錯誤:
julia> super(Union(Float64,Int64))
ERROR: `super` has no method matching super(::Type{Union(Float64,Int64)})
julia> super(None)
ERROR: `super` has no method matching super(::Type{None})
julia> super((Float64,Int64))
ERROR: `super` has no method matching super(::Type{(Float64,Int64)})
更多建議: