Scala 折叠操作中的“递归值X$3需要类型”,即使指定了类型

Scala 折叠操作中的“递归值X$3需要类型”,即使指定了类型,scala,recursion,Scala,Recursion,对于下面的fold调用,我们可以看到已经指示了每个返回值的类型: 注:前三行显示的上述内容实际上都在代码中的一行59上 val (nRows, dfsOut, dfOut): (Int,DataFrameMap, DataFrame) = (1 to nLevels).foldLeft((0, dfsIn, dfIn)) { case ((nRowsPrior, dfsPrior, dfPrior), level) => .. (nnRow

对于下面的fold调用,我们可以看到已经指示了每个返回值的类型:

注:前三行显示的上述内容实际上都在代码中的一行59上

val (nRows, dfsOut, dfOut): (Int,DataFrameMap, DataFrame) 
     = (1 to nLevels).foldLeft((0, dfsIn, dfIn)) {
          case ((nRowsPrior, dfsPrior, dfPrior), level) =>
     ..

   (nnRows, dfs, dfOut1)  // These return values are verified as correctly 
                          // matching the listed return types
}
但我们有以下错误:

Error:(59, 10) recursive value x$3 needs type
val (nRows, dfsOut, dfOut): (Int,DataFrameMap, DataFrame) = (1 to nLevels).foldLeft((0, dfsIn, dfIn)) { case ((nRowsPrior, dfsPrior, dfPrior), level) =>
第10列表示第一个条目nRows,其设置如下:

 val nnRows = cntAccum.value.toInt  
这绝对是一个Int。。因此,根本问题是什么还不清楚


仅供参考,还有另一个标题类似的问题--但这个问题在输出参数中做了一些奇怪的事情,而我的问题是简单的值分配

这是一个没有任何依赖关系的MCVE:

trait DataFrameMap
trait DataFrame

val dfsIn: DataFrameMap = ???
val dfIn: DataFrame = ???
val nLevels: Int = 0

val (_, _) = (1, 2)
val (_, _) = (3, 4)
val (nRows, dfsOut, dfOut): (Int,DataFrameMap, DataFrame) = 
  (1 to nLevels).foldLeft((0, dfsIn, dfIn)) {
    case ((nRowsPrior, dfsPrior, dfPrior), level) =>
    
    val nnRows: Int = nRows
    val dfs: DataFrameMap = ???
    val dfOut1: DataFrame = ???

    (nnRows, dfs, dfOut1)
  }
它准确地再现了错误消息:

错误:递归值x$3需要类型

val (nRows, dfsOut, dfOut): (Int,DataFrameMap, DataFrame) =
     ^
您必须在foldLeft主体内的某个地方使用了nRows、dfsOut或dfsOut。这里编译的很好:

trait DataFrameMap
trait DataFrame

val dfsIn: DataFrameMap = ???
val dfIn: DataFrame = ???
val nLevels: Int = 0

val (_, _) = (1, 2)
val (_, _) = (3, 4)
val (nRows, dfsOut, dfOut): (Int,DataFrameMap, DataFrame) = 
  (1 to nLevels).foldLeft((0, dfsIn, dfIn)) {
    case ((nRowsPrior, dfsPrior, dfPrior), level) =>
    
    val nnRows: Int = ???
    val dfs: DataFrameMap = ???
    val dfOut1: DataFrame = ???

    (nnRows, dfs, dfOut1)
  }
有趣的事实:x$3不是指元组的第三个组件dfOut,而是指整个元组nRows、dfOut、dfOut本身。这就是为什么我必须在val nRows,dfsOut,dfsOut定义之前添加两个,=…,以获得x$3而不是x$1。

问题在于print语句内部:外部foldLeft参数被意外引用,而不是内部循环参数

    info(s"$tag: ** ROWS ** ${props(OutputTag)} at ${props(OutputPath)} count=$nRows")  

$nRows是外部作用域变量:这会导致递归。其意图是引用$nnRows

由于隐私问题,我无法提供MCVE:我已投票表决,但将针对根本原因提供一个单独的答案。@javadba您在谈论什么隐私?上面的代码片段看起来几乎与您已经发布的代码片段完全相同,但它是最小的&可编译的。由于这是一个编译错误,我不会要求您提供完整的可运行代码或真实的输入数据。