【问题标题】:scala - how to infer the return typescala - 如何推断返回类型
【发布时间】:2019-02-12 21:03:51
【问题描述】:

你能解释一下你是如何推断返回类型的吗?见下文。谢谢。

   val examples = sc.textFile(params.input).map { line =>
          Vectors.dense(line.split(' ').map(_.toDouble))
        }

[编辑] 我的意思是你如何推断​​结果类型。谢谢。

【问题讨论】:

  • 返回类型取决于你的代码块的最后一条语句
  • 与其尝试推断结果类型,不如使用类型归属:val x :Int = ... 归属类型,Int,你想要并且认为你应该得到。如果编译器告诉您这不是正确的类型,那么您可以 A)更改归属以匹配实际结果类型,或 B)更改代码以获得您需要的结果类型。

标签: scala types return type-inference


【解决方案1】:

类型推断从后往前工作。

sc.textFile(file).map { line => Vectors.dense(line.split(' ').map(_.toDouble)) }

主表达式中调用的最后一个方法是RDD.map(lambda),它返回一个RDD[whatever the lambda returns]

Vectors.dense(line.split(' ').map(_.toDouble))

那么,在 lambda 主表达式中调用的最后一个方法是 Vectors.dense(doubles),它返回一个 Vector

line.split(' ').map(_.toDouble)

最后这一行没关系,因为Vector没有类型参数,所以没什么可推断的。

所以,如果放在一起,返回类型是 RDD[Vector]。

表达式的类型是其最后一段代码的类型。如果它是带有类型参数的方法,在本例中为 RDD.map[B],则从用于绑定该参数的表达式中推断出该类型参数 B。

为什么要后退?这是一个例子。

def method[T](value:T) = {    
  val a = value    
  val b = a    
  val c = b    
  c 
}

method("Foo")

method("Foo") 返回一个字符串,因为,从后向前 => c的类型,即b类型,即a类型,value类型,即T类型,最后T为String类型。

【讨论】:

    【解决方案2】:

    将其转换为 DenseVector 以推断正确的返回类型

    import org.apache.spark.mllib.linalg.{DenseVector, Vectors}
    import org.apache.spark.rdd.RDD
    
    val examples: RDD[DenseVector] = sc.textFile(file).map { line =>
            Vectors.dense(line.split(' ').map(_.toDouble)).toDense
    }
    

    【讨论】:

      猜你喜欢
      • 2021-10-23
      • 1970-01-01
      • 1970-01-01
      • 2020-03-23
      • 2014-03-05
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多