日本搞逼视频_黄色一级片免费在线观看_色99久久_性明星video另类hd_欧美77_综合在线视频

國內(nèi)最全I(xiàn)T社區(qū)平臺 聯(lián)系我們 | 收藏本站
阿里云優(yōu)惠2
您當(dāng)前位置:首頁 > php開源 > php教程 > Scala之TypeTags and Manifests

Scala之TypeTags and Manifests

來源:程序員人生   發(fā)布時間:2016-11-03 08:45:35 閱讀次數(shù):2548次

注:本文為譯文,原文是Scala官方文檔中的1篇,這里翻譯出來作為本系列的1篇文章。原文鏈接: http://docs.scala-lang.org/overviews/reflection/typetags-manifests.html。 本文原文出處: http://blog.csdn.net/bluishglc/article/details/52596696 嚴(yán)禁任何情勢的轉(zhuǎn)載,否則將拜托CSDN官方保護(hù)權(quán)益!

  • 獲得1個TypeTag
    • 通過typeTagclassTag或weakTypeTag方法
    • 使用TypeTagTClassTagT或WeakTypeTagT的1個隱式參數(shù)
    • 使用類型參數(shù)的Context Bound
  • WeakTypeTags
  • TypeTags和Manifests

猶如所有其他的JVM語言,Scala(在范型中)的類型信息在編譯期都被擦除,這意味著如果你在運行時去檢測1些實例的類型,你可能沒法獲得全部的類型信息,即便Scala的編譯器在編譯時期都知道這些信息。

像scala.reflect.Manifest1樣, TypeTags可以被認(rèn)為是攜帶了編譯期全部類型信息到運行期的對象,例如,TypeTag[T]封裝了在編譯時期肯定的T的實際類型信息,而這些信息可以在運行時期使用(為表述更清晰,本句翻譯在原文基礎(chǔ)上做了調(diào)劑),你要記住,TypeTags可以視作Scala 2.10之前的Manifest類的1個更加豐富的替換者,它完全和Scala的反射系統(tǒng)繼承在了1起。

Scala有3種不同類型的TypeTags

  1. scala.reflect.api.TypeTags#TypeTag,Scala類型的全類型描寫符,例如,TypeTag[List[String]]包括了所有的類型信息,也就是scala.List[String](譯者注:也就是除List類本身,它的范型String類型也被保存并可以獲得)。
  2. scala.reflect.ClassTag,Scala類型的部份類型描寫符,例如,ClassTag[List[String]]只包括被擦除的的類型信息,也就是scala.collection.immutable.List(譯者注:也就是只有List類本身,它的類型參數(shù)String是不會被保存的)。ClassTag只提供了訪問1個類型的運行時的類型信息,類似于scala.reflect.ClassManifest。
  3. scala.reflect.api.TypeTags#WeakTypeTag,抽象類類型的描寫符(參考后文)。

獲得1個TypeTag

猶如Manifest,TypeTag總是由編譯器生成的,可以通過3種方式獲得。

通過typeTag,classTag或weakTypeTag方法

你可以通過typeTag方法直接獲得某個特定類型的TypeTag,typeTag方法在Universe。

例如, 獲得Int型的1個TypeTag:

import scala.reflect.runtime.universe._ val tt = typeTag[Int]

或獲得String型的1個ClassTag:

import scala.reflect._ val ct = classTag[String]

這些方法基于給定的類型參數(shù)T構(gòu)建了TypeTag[T] 或ClassTag[T]的實例(譯者注:在編譯期由編譯器自動完成)。

使用TypeTag[T],ClassTag[T]或WeakTypeTag[T]的1個隱式參數(shù)

像Manifest1樣,你實際上可以要求編譯器去生成1個TypeTag, 這可以通過指定1個TypeTag[T]的隱式的“跡象”(evidence)參數(shù)來實現(xiàn)。如果編譯器在編譯期間沒能找到匹配的隱式值,編譯器就會自動創(chuàng)建1個TypeTag[T]的實例(譯者注:固然,這時候類型T已肯定)。

注意:在方法和類上使用TypeTag[T],ClassTag[T]或WeakTypeTag[T]的1個隱式參數(shù)的做法是很常見的。

例如,我們可以寫1個接受任何類型做參數(shù)的方法,然后通過TypeTag打印這個參數(shù)的類型信息:

import scala.reflect.runtime.universe._ def paramInfo[T](x: T)(implicit tag: TypeTag[T]): Unit = { val targs = tag.tpe match { case TypeRef(_, _, args) => args } println(s"type of $x has type arguments $targs") }

在這里,我們寫了1個范型方法paramInfo,同時提供了1個隱式參數(shù)(implicit tag: TypeTag[T])。然后我們就能夠直接獲得類型信息(TypeTag的tpe方法返回的是T的Type實例)。

(譯者注:上述方法的意圖是:如果T是援用類型(TypeRef),獲得它的類型參數(shù)列表。)

我們可以這樣使用我們的paramInfo方法。

scala> paramInfo(42) type of 42 has type arguments List() scala> paramInfo(List(1, 2)) type of List(1, 2) has type arguments List(Int)

(譯者注:targs 本身是1個List,42是簡單類型,沒有類型參數(shù),所以是1個空的List,List(1, 2)明顯是1個List[Int],所以它的類型參數(shù)是Int)

使用類型參數(shù)的Context Bound

1種更加簡單地實現(xiàn)上述目標(biāo)的做法是使用1個類型參數(shù)的Context Bound。不同于提供1個獨立的隱式參數(shù),你可以像下面這樣把TypeTag簡單的加到類型參數(shù)列表中:

def myMethod[T: TypeTag] = ...

基于給定的上下文邊界[T: TypeTag],編譯器會簡單地生成1個TypeTag[T]的隱式參數(shù),然后把方法重寫成像前1個帶隱式參數(shù)的例子那樣。

上面使用上下文邊界的例子會被(編譯器)重寫為:

import scala.reflect.runtime.universe._ def paramInfo[T: TypeTag](x: T): Unit = { val targs = typeOf[T] match { case TypeRef(_, _, args) => args } println(s"type of $x has type arguments $targs") } scala> paramInfo(42) type of 42 has type arguments List() scala> paramInfo(List(1, 2)) type of List(1, 2) has type arguments List(Int)

WeakTypeTags

WeakTypeTag[T]泛化了TypeTag[T]。不像1個常規(guī)的TypeTag,它的類型描寫組件可以指向類型參數(shù)或抽象類型,但是,WeakTypeTag[T]總是盡量的具體化。比如,如果被援用類型參數(shù)或抽象類型的類型標(biāo)簽是可用的,它們通常會被嵌入到WeakTypeTag[T]的具體類型中去。讓我們繼續(xù)上面的例子:

import scala.reflect.runtime.universe._ def weakParamInfo[T](x: T)(implicit tag: WeakTypeTag[T]): Unit = { val targs = tag.tpe match { case TypeRef(_, _, args) => args } println(s"type of $x has type arguments $targs") } scala> def foo[T] = weakParamInfo(List[T]()) foo: [T]=> Unit scala> foo[Int] type of List() has type arguments List(T)

TypeTags和Manifests

寬泛地說,TypeTags相當(dāng)于2.10版本之前的scala.reflect.Manifests是相1致的。而scala.reflect.ClassTag相當(dāng)于cala.reflect.ClassManifest,scala.reflect.api.TypeTags#TypeTag最貼近scala.reflect.Manifest。其他2.10版本之前的Manifest類型就沒有對應(yīng)的”Tag”類型了。

  • scala.reflect.OptManifest不再被支持,由于Tag類可以具體化到任意類型,所以它們總是可用的。
  • 沒有scala.reflect.AnyValManifest的等價物。相應(yīng)地,你可以用base Tag比較它們的Tag以便找出是不是它表示的是1個primitive value class。另外,它還可以簡單的使用.tpe.typeSymbol.isPrimitiveValueClass
  • Manifest伴生對象中定義的工廠方法也沒有替換物
  • 某些 manifest 的操作如(i.e., <:<, >:> and typeArguments)都不再被支持。

在Scala 2.10里,scala.reflect.ClassManifests不再被推薦使用!scala.reflect.Manifest也將被TypeTags和ClassTag所代表的風(fēng)格所取代。

生活不易,碼農(nóng)辛苦
如果您覺得本網(wǎng)站對您的學(xué)習(xí)有所幫助,可以手機(jī)掃描二維碼進(jìn)行捐贈
程序員人生
------分隔線----------------------------
分享到:
------分隔線----------------------------
關(guān)閉
程序員人生
主站蜘蛛池模板: 亚洲精品日韩综合观看成人91 | 国产专区精品 | 九九精品视频在线观看 | 欧美a级成人淫片免费看 | 欧美激情五月 | 国产激情一区二区三区在线观看 | 国产三级免费观看 | 色综合色综合色综合色综合 | 国产真人真事毛片视频 | 成人影视电影 | 久久在线看 | 精品少妇久久久久久888优播 | 成年人视频免费在线观看 | 天堂av一区二区 | 欧美综合图 | 男女爱爱网站 | 久久精品二区 | 亚洲国产精品久久久 | 99精品一区二区 | 99青草 | 久久精品夜夜夜夜夜久久 | 久久久精品免费观看 | 国产二区电影 | 久久精品欧美一区二区 | 夫妻av | 国产黄大片在线观看 | 中文字幕资源在线 | 久久91精品国产 | 亚洲成人天堂 | 国产在线精品自拍 | 久久福利免费视频 | 国产一区二区精品 | 国产精品国产三级国产a | 精品99久久久 | 日韩在线中文 | 九九久久国产 | 91香蕉一区二区三区在线观看 | 91久久国产精品 | 久久亚洲视频 | 99国产精品视频免费观看一公开 | 亚洲高清自拍 |