3

Scala:是否可以将类型参数限制为非抽象的?

除了类型参数和抽象类型成员的视图边界、上限和下限之外,是否还有其他约束?例如,在我熟悉的 C# 中,您有额外的通用约束:

where T: Class //不确定 T<: AnyRef 是否包含在 Scala 中

其中T:接口

其中 T:结构

where U: T //裸类型约束

where T: new () //这确保了类型参数是非抽象的,并允许在泛型类中实例化该类型的对象。

最后一个特别重要,因为它允许您构造未知类型,但遗憾的是您只能禁止无参数构造函数。

=:= <:< 和 <%< 只能用于方法参数吗?

作为对评论的回应,该问题的直接触发因素是需要“T:new()”约束或某种等效机制。

class ExampleClass[T <: AnyRef] {
  val example: T = new T()//Won't compile as the compiler  
} //doesn't know if such a constructor exists

某些 C# 约束的使用特定于 C# 的需要。例如,人们一直想要的 C# 中没有的一个限制是“T: numericType” 这个问题已经在 Scala 中解决了。我仍然非常了解 Scala 语言,所以除了上述内容之外,我只是想明确说明在 Scala 语法的这个方面哪些工具是可用的,哪些工具不可用,即使我没有确切地知道我可能想如何在 Scala 上下文中使用它们。

我不确定这是否完全相关,但有时编译器(Eclipse 2.1.0.M1 和 Eclipse 3.7.2)似乎不允许我实例化未知元素类型的集合。下面的代码现在似乎编译得很好。所以我想知道规则是什么:

abstract class Descrip [T <: DTypes]()
{      
  val hexs: MutableList[T#HexT] = new  MutableList[T#HexT] //compiles fine
  val sides: MutableList[T#SideT] = new MutableList[T#SideT] //compiles fine
}
4

1 回答 1

1

的需要new T()通常通过使用Manifests 来解决。例如这段代码编译:

class ExampleClass[T: Manifest] {
  val example: T = manifest[T].erasure.newInstance().asInstanceOf[T]
}

缺点是,如果实例化的TforExampleClass没有无参数构造函数,它将在运行时失败......

关于Numeric,Ordering等,它们是类型类并且是标准库的一部分,而不是语言的一部分。您可以构建自己的类型类。的情况Manifest很特殊,因为它确实得到了语言的支持以提供隐式对象。

于 2012-05-24T23:12:25.413 回答