【发布时间】:2013-11-14 10:45:58
【问题描述】:
在 scala 中指定以下概念的最佳方式是什么?该概念表示通用提取器函数的接口,该函数指定了在编译时提取的类。
结构定义
import org.jsoup.Jsoup
import org.jsoup.nodes.Document
import scala.collection.JavaConversions._
trait ExtractorBase {
type ExtractedType
type RetType = Tuple2[Option[Seq[ExtractedType]],Option[Seq[String]]]
type ExtractorFunction = (Document) => RetType
def extractor : ExtractorFunction
}
class Extractor[T] (extractor_in: Any) extends ExtractorBase {
type ExtractedType = T
val extractor : ExtractorFunction = extractor_in
}
结构实例
//type TFunc = (Document) => Tuple2[Option[Seq[Int]],Option[Seq[String]]]
val ex = new Extractor[Int]( (x: Document)=> {
(Some(Seq(1)),Some(Seq("hassan")))
})
目前提取器函数的别名也没有正确:
[error] /Users/hassan/code/scala/extractor/hon.scala:14: type mismatch;
[error] found : Any
[error] required: org.jsoup.nodes.Document => (Option[Seq[Extractor.this.ExtractedType]], Option[Seq[String]])
[error] (which expands to) org.jsoup.nodes.Document => (Option[Seq[T]], Option[Seq[String]])
[error] val extractor : ExtractorFunction = extractor_in
-
如何在扩展特征的类定义之外引用通用特征数据?在编译时和运行时。例如编译时间我宁愿有:
特征提取器基础[T] { 类型 ExtractedType = T 类型 RetType = Tuple2[Option[Seq[ExtractedType]],Option[Seq[String]]] 类型 ExtractorFunction = (Document) => RetType def 提取器:ExtractorFunction }
然后
class Extractor[T] (extractor_in: ExtractorBase[T].ExtractorFunction) extends ExtractorBase
有点类似于 C++ 特征。
在运行时,我也不介意获取 trait 中的类型信息。
可能有一种更惯用的方式来创建特征实例,我不想通过
Extractor[T]类。有没有办法用 trait 的伴生对象来做到这一点?
编辑
Ankur 的回答让我走上了正确的道路。我的曲目中缺少 # 运算符。是时候打扮一下了。
trait ExtractorBase[T] {
type ExtractedType = T
type RetType = Tuple2[Option[Seq[ExtractedType]],Option[Seq[String]]]
type ExtractorFunction = (Document) => RetType
def extractor : ExtractorFunction
}
class Extractor[T] (extractor_in: ExtractorBase[T]#ExtractorFunction) extends ExtractorBase[T] {
def extractor : ExtractorBase[T]#ExtractorFunction = extractor_in
}
导致:
val ex = new Extractor[Int]( (x: Document)=> {
(Some(Seq(1)),Some(Seq("hassan")))
})
【问题讨论】:
标签: scala template-meta-programming generic-programming