Spark 2.4中将DataFrame转为Dataset时出现编码器找不到错误
解决Spark Dataset编码器找不到的编译错误
嘿,这个问题我太熟了!你遇到的编译错误核心原因是你把Characters这个case class定义在main方法的内部了。Spark的隐式编码器(Encoder)对于case class这类Product类型的支持,要求case class的定义必须在方法作用域之外——要么是顶层类,要么是包含main方法的对象内部(但要在main外面)。
为什么会这样呢?因为方法内部定义的类属于局部类,Spark的spark.implicits._没办法为这种局部类生成对应的隐式编码器实例,编译器自然就报错说找不到Encoder[Characters]了。
给你改好的代码,把case class移到RunnerTest对象外面就行:
import org.apache.spark.sql.SparkSession // 把case class移到顶层作用域,或者放在RunnerTest对象内部、main方法之外也行 case class Characters(name: String, id: Int) object RunnerTest { def main(args: Array[String]): Unit = { val spark = SparkSession.builder.appName("SparkSessionExample") .master("local[4]") .config("spark.sql.warehouse.dir", "target/spark-warehouse") .getOrCreate import spark.implicits._ val path = "examples/src/main/resources/Characters.csv" // 额外提醒:如果你的CSV文件有表头,一定要加header=true选项,不然列名会不匹配 val peopleDS = spark.read .option("header", "true") .csv(path) .as[Characters] } }
顺便提个小细节:如果你的CSV文件第一行是表头(比如"name,id"),一定要加上.option("header", "true"),否则Spark会默认把第一行数据当成列名(命名成_c0、_c1这类),这样和你的case class字段名对应不上,后续可能还会出现类型转换或者字段不匹配的问题。
内容的提问来源于stack exchange,提问作者Achilleus
相关产品推荐
相关产品推荐

