【问题标题】:in what cases does scala properly convert String to java.lang.String在什么情况下 scala 正确地将 String 转换为 java.lang.String
【发布时间】:2016-07-03 06:11:24
【问题描述】:

说我做一个单参数泛型方法:

trait MyTrait[T] {
  def method():T
}

然后扩展它并参数化。这个:

class MyClass extends MyTrait[java.lang.String] {
  def method() = "foo"
}

和这个是一样的:

class MyClass extends MyTrait[String] {
  def method() = "foo"
}

但是,当您创建一个像这样参数化 lambda 的特征方法时:

trait MyTrait {
  def apply[T](input:()=>T):T
}

那你就没那么幸运了。这个:

class MyClass extends MyTrait {
  def apply(input:()=>java.lang.String) = "foo"
}

会导致这个:

Error:(25, 45) type mismatch;
 found   : java.lang.String("foo")
 required: String
      def apply[String](input:()=>String) = "foo"
                                    ^

不过,这很好:

class MyClass extends MyTrait {
  def apply[String](input:()=>String) = new String("foo")
}

那么在什么情况下 scalac 真正知道需要进行转换而在什么情况下不知道呢?

此外,即使我写出了 java.lang.String 类型的整个路径

class MyClass extends MyTrait {
  def apply[java.lang.String](input:()=>java.lang.String) = new java.lang.String("foo")
}

它抛出另一个错误:

Error:(25, 21) ']' expected but '.' found.
      def apply[java.lang.String](input:()=>java.lang.String) = new java.lang.String("foo")
                    ^

如果我想通过直接模板化 java.lang.String 来实现后一种方式,我该怎么做?

【问题讨论】:

  • def apply[String] 你在这里声明了一个名为String 的类型参数。

标签: java string scala templates generics


【解决方案1】:

这个

class MyClass extends MyTrait {
  def apply[String](input:()=>String) = new String("foo")
}

不好。结果为class type required but String found。这里的问题是,当您使用参数化方法扩展类时,您没有声明类型参数是什么。在使用方法时声明它。

让我们重写一下:

class MyClass extends MyTrait {
  def apply[String](input:()=>String) = input()
}

现在观察:

scala> (new MyClass).apply[String](() => "foo")
res0: String = foo

scala> (new MyClass).apply[Int](() => 5)
res1: Int = 5

它起作用是因为当你声明这个时:

  def apply[String](input:()=>String) = input()

String参数的名称。如果您在上面写了TXyzzyManISuckAtTypeParameters 而不是String,那就完全一样了。你是说你会得到一个类型参数,你会命名类型参数String,这是返回函数的值,通过覆盖,apply 方法的值。

当我调用apply[Int](() => 5) 时,Scala 会将定义中的String替换Int

【讨论】:

  • 哎呀,我真傻。感谢您的精彩回复。
猜你喜欢
  • 2012-09-30
  • 2022-01-12
  • 2021-04-12
  • 2017-05-30
  • 2014-07-11
  • 2011-05-28
  • 1970-01-01
  • 2012-08-22
  • 2021-10-19
相关资源
最近更新 更多