Scala語言中的隱式轉換是一個十分強大的語言特性,主要可以起到兩個作用:
成都創(chuàng)新互聯(lián)公司長期為千余家客戶提供的網站建設服務,團隊從業(yè)經驗10年,關注不同地域、不同群體,并針對不同對象提供差異化的產品和服務;打造開放共贏平臺,與合作伙伴共同營造健康的互聯(lián)網生態(tài)環(huán)境。為武鄉(xiāng)企業(yè)提供專業(yè)的成都網站建設、網站制作,武鄉(xiāng)網站改版等技術服務。擁有十余年豐富建站經驗和眾多成功案例,為您定制開發(fā)。
一.自動進行某些數(shù)據(jù)類型的隱式轉換
String類型是不能自動轉換為Int類型的,所以當給一個Int類型的變量或常量賦予String類型的值時編譯器將報錯。所以,一下語句是錯誤的。
val x: Int = "100"
如果需要將一個字符串類型的整形數(shù)值賦給Int,比如使用String.toInt方法,例如:
val x: Int = "100".toInt
如果想讓字符串自動轉換為整形,就可以使用隱式轉換??梢远x如下函數(shù)。
implicit def strToInt(str: String) = str.toInt
這時你再對Int類型的變量賦值字符串時,字符串就會自動轉換為Int。
scala> val x:Int = "00" x: Int = 100
如果你此時定義一個兩數(shù)相加的函數(shù)
def add(x: Int, y: Int) = x + y
就可以達到這種效果:
scala> add("100", 200) res1: Int = 300
隱式轉換有一定的使用規(guī)則,比較重要的有2個。
1.按照《Scala編程》這本書中所說:插入的隱式轉換必須以單一標識符的形式處于作用域中,或與轉換的源或目標類型關聯(lián)在一起。Scala編譯器將僅考慮處于作用域之內的隱式轉換。
簡而言之,就是在使用隱式轉換之前,需要用import把隱式轉換引用到當前的作用域里或者就在作用域里定義隱式轉換。除了隱式轉換被引入進當前作用域之外,還有一種方式可以使用隱式轉換,就是編譯器會在源類型或者期望的伴生對象中尋找隱式定義。
2.無歧義規(guī)則:隱式轉換只能在無其他可用轉換的前提下才能操作。如果在同一作用域里,對同一源類型定義一個以上的隱式轉換函數(shù),如果多種隱式轉換函數(shù)都可以匹配,那么編譯器將報錯,所以在使用時請移除不必要的隱式定義。
二.隱式參數(shù)
柯里化函數(shù)會有多個參數(shù)列表,當希望對某個參數(shù)列表采用默認參數(shù)時,可以使用implicit提供的隱式參數(shù)功能。做法是在需要自動填充的參數(shù)列表最開端加上implicit,然后在定義域內定義需要填充的默認參數(shù)值常量,并在常量的定義之前聲明implicit。
視界
當有如下定義時
class Container[A <% Int] { def addIt(x: A) = 123 + x }
表示A類型必須可視為Int。簡單的說,就是需要有一個轉換函數(shù),可以自動的將A類型,轉換為Int類型,如果沒有這樣的轉換函數(shù),可以使用implicit定義。
寫一個類測試一下Scala中的隱式轉換的用法:
class Fraction(n: Int, d: Int) { // def den = d private val den = d; // def num = n 類參數(shù)定義為方法或字段都可以 private val num = n; // 定義乘法 def *(other: Fraction) = Fraction(other.num * this.num, other.den * this.den) // 重寫toString override def toString() = s"$num / $den" } //伴生對象 object Fraction { // implicit隱轉 方法名無關可以隨意改,自動調用 implicit def int2Fraction(n: Int) = Fraction(n, 1) def apply(n: Int, d: Int) = { new Fraction(n, d) } def unapply(frac: Fraction) = if (frac.den == 0) None else Some((frac.num, frac.den)) } object TestFrac extends App{ // 3 隱式調用了int2Fraction方法被轉化為一個Fraction對象Fraction(3,1) val result = 3 * Fraction(4,5) // 也可以顯示調用 val result2 = Fraction.int2Fraction(5) * Fraction(3,4) println(result) // unapply val Fraction(num,den) = result println(num,den) }
以上就是本文的全部內容,希望對大家的學習有所幫助,也希望大家多多支持創(chuàng)新互聯(lián)。