时间戳转换Spark Scala

时间:2019-05-15 11:52:35

标签: apache-spark pyspark apache-spark-sql

我在pyspark中有一个UDF,如下所示,可以将字符串转换为时间戳

@udf(returnType=TimestampType())
def to_timestamp(dt):
    return parse(dt)
  

TimestampType-从pyspark.sql.types导入TimestampType

我想将其转换为Scala(火花),我尝试如下所示,但未选择参数

def toTimestampFormat(dt: String): TimestampType= {
    return unix_timestamp(dt, "yyyyMMdd'T'HHmmss:SSSSSS").cast(TimestampType)
}

我在其中缺少什么吗?

1 个答案:

答案 0 :(得分:1)

您无需创建UDF即可将字符串转换为时间戳,只需通过调用unix_timestamp方法使用Spark SQL中的with_column函数即可:

dataframe.withColumn("timestamp", unix_timestamp($"date", "yyyyMMdd'T'HHmmss:SSSSSS"))

第一个参数是字符串格式的日期所在的列。第二个是该字符串的格式。

别忘了导入unix_timestamp函数和Spark隐式函数以使用$运算符:

import org.apache.spark.sql.functions.unix_timestamp
import spark.implicits._

希望有帮助!

编辑

如果您确信要在UDF中执行此操作,则不能使用其中的unix_timestamp,因为它必须接收一个Spark列对象,并且在定义UDF时,您可以不要使用列对象,而是使用该列的实际值。这就是为什么 在您的代码中,unix_timestamp 没有选择参数。此外,您创建的用于定义UDF的函数必须返回Scala本机数据类型而不是Spark列数据类型,因此在此类函数中返回TimestampType毫无意义。

要将字符串转换为UDF中的时间戳,您需要一个接受字符串并返回Long对象的函数。在此示例中,我通过使用Joda-Time Scala库来定义所需的UDF:

  val toTimestampFormat = udf((dt: String) => {
    val formatter = DateTimeFormat.forPattern("yyyyMMdd'T'HHmmss")
    formatter.parseDateTime(dt).getMillis
  })

最后,这就是您使用此UDF的方式:

dataframe.withColumn("timestamp", toTimestampFormat(col("date")))

编辑2

如果您希望列数据类型为TimestampType,则UDF中的函数必须返回一个java.sql.Timestamp对象:

  val toTimestampFormat = udf((dt: String) => {
    val formatter = DateTimeFormat.forPattern("yyyyMMdd'T'HHmmss")
    new Timestamp(formatter.parseDateTime(dt).getMillis)
  })