在pyspark中将Unix(Epoch)时间更改为本地时间

Posted

技术标签:

【中文标题】在pyspark中将Unix(Epoch)时间更改为本地时间【英文标题】:change Unix(Epoch) time to local time in pyspark 【发布时间】:2018-06-16 19:54:01 【问题描述】:

我在 Spark 中有一个数据框,其中包含 Unix(Epoch) 时间和时区名称。我希望根据不同的tz名称将epochtime转换为本地时间。 这是我的数据的样子:

data = [
    (1420088400, 'America/New_York'),
    (1420088400, 'America/Los_Angeles'),
    (1510401180, 'America/New_York'),
    (1510401180, 'America/Los_Angeles')]

df = spark.createDataFrame(data, ["epoch_time", "tz_name"])

df.createOrReplaceTempView("df")
df1 = spark.sql("""select *, from_unixtime(epoch_time) as gmt_time,"
               from_utc_timestamp(from_unixtime(epoch_time), tz_name) as local_time"
               from df""")
df1.show(truncate= False)

结果如下:

+----------+-------------------+-------------------+---------------------+
|epoch_time|tz_name            |gmt_time           |local_time           |
+----------+-------------------+-------------------+---------------------+
|1420088400|America/New_York   |2015-01-01 05:00:00|2015-01-01 00:00:00.0|
|1420088400|America/Los_Angeles|2015-01-01 05:00:00|2014-12-31 21:00:00.0|
|1510401180|America/New_York   |2017-11-11 11:53:00|2017-11-11 06:53:00.0|
|1510401180|America/Los_Angeles|2017-11-11 11:53:00|2017-11-11 03:53:00.0|
+----------+-------------------+-------------------+---------------------+
    我不太确定这种转移是否正确,但似乎夏令时已经解决了。

    我是否应该先使用from_unixtime将epochtime更改为时间字符串,然后使用to_utc_timestamp将其更改为utc时间戳,最后使用tz_name将此UTC时间戳更改为本地时间?试过了,但是出错了

    df2 = spark.sql("""select *, from_unixtime(epoch_time) as gmt_time,
                       from_utc_timestamp(from_unixtime(epoch_time), tz_name) as local_time,
                       from_utc_timestamp(to_utc_timestamp(from_unixtime(epoch_time),from_unixtime(unix_timestamp(), 'z')), tz_name) as newtime from df""")
    

    如何查看我的 EMR 服务器时区?

    试过了,这是服务器时区吗?

    spark.sql("select from_unixtime(unix_timestamp(), 'z')").show()
    

    这给了我:

    +--------------------------------------------------------------------------+
    |from_unixtime(unix_timestamp(current_timestamp(), yyyy-MM-dd HH:mm:ss), z)|
     +--------------------------------------------------------------------------+
    |                                                                       UTC|
    +--------------------------------------------------------------------------+
    

感谢您的澄清。

【问题讨论】:

错误是什么?对我来说很好。 您使用的是什么版本的 Spark? Spark 2.0 。我在 EMR 控制台console.aws.amazon.com/console/home?region=us-east-1 上检查了它,其中区域是 us-east-1。如何检查服务器时区名称? 你知道 spark.sql("select from_unixtime(unix_timestamp(), 'z')") 'z' 代表for吗? 【参考方案1】:

当您调用 from_unixtime 时,它将根据您的 Java 运行时的时区格式化日期,因为它只是使用 SimpleDateFormat here 的默认时区。在您的情况下,它是 UTC。因此,当您将值转换为本地时间时,您只需调用 from_utc_timestamp 并传入 tz_name 值。但是,如果您要更改系统时区,则需要先调用 to_utc_timestamp

Spark 2.2 引入了时区设置,因此您可以像这样为 SparkSession 设置时区

spark.conf.set("spark.sql.session.timeZone", "GMT")

在这种情况下,时间函数将使用 GMT 而不是您的系统时区,请参阅源代码 here

【讨论】:

感谢您的回答,它解释了我所缺少的部分内容。为什么我从控制台检查 EMR 服务器是 us-east-1 区域,但从 spark.sql("select from_unixtime(unix_timestamp(), 'z')").show() 是 UTC?如果我为我的 SparkSession 设置时区,那只会在我当前的 Spark 会话中吗?如果我在我的代码中停止这个会话,当我开始另一个会话时,我需要重新设置它吗?谢谢。 你可以在你的 spark 配置中设置它,例如使用 spark-shell --conf spark.sql.session.timeZone=GMT

以上是关于在pyspark中将Unix(Epoch)时间更改为本地时间的主要内容,如果未能解决你的问题,请参考以下文章

如何在 PySpark 中将 unix 时间戳列转换为人类可理解的时间戳? [复制]

在Android中将Epoch时间转换为日期并将日期转换为Epoch时间[重复]

ESP8266-通过NTP获取 Epoch/Unix(时间戳)时间

Razor 视图中的 Epoch/Unix 时间戳(以毫秒为单位)到日期时间

如何在 Redshift 中将时间戳(具有毫秒)转换为 EPOCH

在pyspark中将字符串价格值转换为double类型