Spark SQL表最大列数

时间:2016-02-24 08:16:21

标签: scala apache-spark-sql

我试图通过在列数为200+的Scala程序中创建RDD来创建spark SQL表。当我创建模式时,编译(sbt compile)失败并出现java.lang.StackOverflowError异常:

use TesseractOCR;

不能粘贴堆栈跟踪,因为它超过1.5k行

在将列数减少到大约100-120时,编译成功。此外,当我使用模式字符串创建模式(拆分模式字符串然后创建它的映射)时,编译成功(标题&#34下的第一个示例; 以编程方式指定模式"在{ {3}})。

手动指定导致异常的模式似乎有什么问题?

1 个答案:

答案 0 :(得分:3)

这里的基本问题是您在每个StructField的每个步骤中进行列表连接。 operator ::实际上是List not StructField的成员。代码如下:

val fields = field1 :: field2 :: field3 :: Nil

这相当于:

val fields = field1 :: (field2 :: (field3 :: Nil))

甚至

val fields = Nil.::(field1).::(field2).::(field3)

因此,在执行时,JVM需要递归计算对::方法的调用。 JVM正在增加堆栈的深度,与列表中的项目数成比例。拆分字符串字符串和映射的原因是因为它遍历字段名称的拆分字符串而不是使用递归。

这不是Spark问题。一旦进入数百个项目,您就可以在Scala repl中的任何类型的一系列List连接上重现相同的堆栈溢出错误。只需使用其他方法之一来创建不会导致堆栈溢出的StructField列表。

例如,像这样的东西可以正常工作:

val structure = StructType(
  List(
    StructField("RT", StringType,nullable = true),
    StructField("SERIALNO", StringType,nullable = true),
    StructField("SPORDER", StringType,nullable = true),
    // Other Fields
    StructField("LASTFIELD", StringType,nullable = true)
  )
)