對象包語法相比簡單地讓函數和變量添加到包中有什麼優勢?Scala包對象背後的動機
例如:
package object something {
def hello = 0
}
package something {
}
爲什麼不乾脆:
package something {
def hello = 0
// other classes and such
}
對象包語法相比簡單地讓函數和變量添加到包中有什麼優勢?Scala包對象背後的動機
例如:
package object something {
def hello = 0
}
package something {
}
爲什麼不乾脆:
package something {
def hello = 0
// other classes and such
}
你甚至可以更進一步:爲什麼有包可言,當我們有object
S'
Scala旨在用作「託管語言」,即可以很好地託管在另一種語言的平臺之上的語言。 Scala的原始實現是在Java平臺和ISO通用語言基礎架構平臺上(或者說它的主要實現,.NET和Mono)。今天,我們也在ECMAScript平臺(Scala.js)上實現了一個實現,例如,Java平臺實現也可以在Android上使用。你也可以想象其他有趣的平臺,你想運行Scala,例如在Windows UWP平臺,斯威夫特/的Objective-C /核心基金/ MacOS的/的iOS/tvOS/watchOS平臺,侏儒/ GObject的平臺,Qt的/ C++平臺等
Scala沒有只是打算在這些平臺上運行,它打算滿足兩個,往往相互衝突,目標:
小號o,在斯卡拉,執行問題是語言設計的一部分。 (Clojure的設計師Rich Hickey曾在一次演講中表示「JVM是而不是的實現細節」,這同樣適用於Scala)。一個很好的例子是正確的尾部調用:爲了支持正確的尾部調用,Scala必須管理自己的堆棧,而不是在JVM等平臺上使用主機平臺的本地調用堆棧,但這意味着您不能再輕鬆地從平臺上的其他代碼調用Scala代碼,反之亦然。所以,雖然適當的尾部調用會很好,但Scala會處理不太強大的適當的立即尾部遞歸。
理論上,Scala中只需要object
S,trait
S,方法,type
s和路徑(.
和#
)。其他一切基本上都是爲了簡化與主機平臺的集成。這包括,例如,null
,class
es和package
s。
理想情況下,應該有一個從宿主平臺構造到Scala構造的簡單映射,反之亦然。因此,例如,Scala方法和JVM方法之間有一個簡單的映射。 JVM接口和Scala特性之間的簡單映射只有抽象成員。有Scala特性和JVM類之間的簡單映射,這就是爲什麼Scala也有類(冗餘)概念的原因。同樣,在Scala object
和JVM package
(或CLI namespace
s)之間也沒有簡單的映射,這就是爲什麼Scala也有(冗餘)概念package
的原因。
然而,我們真的像package
S(其中,畢竟,有些像斯卡拉object
S)擁有成員。但JVM package
和CLI namespace
s不能有除interface
s和class
es之外的成員,並且由於我們僅在Scala中介紹它們以與主機平臺兼容,因此它們與主機平臺不兼容是沒有意義的通過添加成員給他們。
因此,我們引入了另一個單獨的概念,package object
,它擁有我們想要添加到package
的成員,但不能,因爲主機平臺的互操作性。
TL;博士:
package
S(儘管我們已經有了object
s,它可以做同樣的事情package
S)package
s有會員package
s不能有會員,因爲interoppackage object
s作爲同伴package
s感謝您的回答。所以原因只在於實施限制。我想知道這是否也是爲了避免將包方法/字段分散到多個文件中。 – Derlin
@Derlin理論上你可以從不同的文件中獲取所有頂級的defs,vals,types,...並將它們編譯成一個包對象。但我認爲這會導致增量和單獨編譯的問題。 –
不確定你的意思是「簡單地讓你添加函數和變量到一個包」。包對象旨在提供包中的常量。 –
增加了一個例子。 – Derlin