类型参数[T]不符合方法产品的类型参数范围[T <:产品]

时间:2020-04-08 09:49:08

标签: scala apache-spark generics

我想使用此代码读取csv文件。但这会导致泛型错误。为什么?我认为我被指定为“”之类的类型。

def readMoviesData[T](spark: SparkSession, dataPath: String): Dataset[T] = {
  import spark.implicits._
  spark.read.format("csv").schema(Encoders.product[T].schema)
    .option("header","true").load(dataPath).as[T]
}

def analysisMovies(dataPath: String): Unit = {
  val spark = SparkSession.builder().appName("analysis movies data").getOrCreate()
  val movies: Dataset[MovieModel] = readMoviesData(spark, dataPath + "/movies.csv")
  movies.createOrReplaceTempView("movies")
  spark.sql("select count(*) from movies")
}

错误

Error:(10, 53) type arguments [T] do not conform to method product's type parameter bounds [T <: Product]
spark.read.format("csv").schema(Encoders.product[T].schema)

2 个答案:

答案 0 :(得分:2)

尝试在T边界中添加Product : TypeTag,并为T使用隐式编码器:

import scala.reflect.runtime.universe.TypeTag
def readMoviesData[T <: Product : TypeTag](spark: SparkSession, dataPath: String): Dataset[T] = {
  implicit val encoder: Encoder[T] = Encoders.product[T]
  spark.read.format("csv").schema(encoder.schema)
    .option("header","true").load(dataPath).as[T]
}

答案 1 :(得分:2)

错误消息显示:

product期望其类型参数是Product的子类型,但是您的类型参数不受限制,因此可以是任何东西,包括不是Product子类型的东西。

因此,一种解决方法是确保将T限制为Product的子类型。