【问题标题】:How to compute difference between timestamps with PySpark Structured Streaming如何使用 PySpark 结构化流计算时间戳之间的差异
【发布时间】:2019-11-14 13:46:28
【问题描述】:

我在 PySpark 结构化流中遇到以下问题。

我的流数据中的每一行都有一个用户 ID 和一个时间戳。现在,对于每一行和每个用户,我想添加一个时间戳不同的列。

例如,假设我收到的第一行是:“用户 A,08:00:00”。如果第二行显示“用户 A,08:00:10”,那么我想在第二行添加一个名为“间隔”的列,表示“10 秒”。

有没有人知道如何做到这一点?我尝试使用结构化流文档的窗口函数示例,但没有用。

非常感谢

【问题讨论】:

  • 无用是什么意思?据我所知,结构化流不支持像延迟这样的传统窗口函数。
  • 我的意思是我没有找到用“流”窗口模拟滞后函数的方法。对我来说,Spark 没有提供表现为延迟的函数似乎令人难以置信。

标签: apache-spark pyspark spark-structured-streaming


【解决方案1】:

因为我们谈论的是结构化流和“每一行和每个用户”,这告诉我您应该使用带有某种流聚合的流查询(groupBy 和 @987654324 @)。

对于流式聚合,您只能依靠结构化流中的微批量流执行。这使得单个用户的记录可以是两个不同微批次的一部分。这让你需要一个状态。

综上所述,您需要有状态的流式聚合。

有了这个,我想你想要Arbitrary Stateful Operations之一,即KeyValueGroupedDataset.mapGroupsWithStateKeyValueGroupedDataset.flatMapGroupsWithState(见KeyValueGroupedDataset):

许多用例需要比聚合更高级的有状态操作。例如,在许多用例中,您必须从事件的数据流中跟踪会话。为了进行这种会话化,您必须将任意类型的数据保存为状态,并使用每个触发器中的数据流事件对状态执行任意操作。

从 Spark 2.2 开始,这可以使用操作 mapGroupsWithState 和更强大的操作 flatMapGroupsWithState 来完成。这两种操作都允许您在分组数据集上应用用户定义的代码来更新用户定义的状态。

状态将是每个用户找到的最后一条记录。看起来可行。

我担心的是:

  1. 这个流式查询要处理多少用户? (越多状态越大)

  2. 何时清理状态(不再期望在流中的用户)? (这将保持合理大小的状态)

【讨论】:

  • +1 非常感谢。似乎这仅在 Scala 语言中可用。你能提供一个代码示例吗?
  • 啊,对。它意味着在 pyspark 中。对此感到抱歉。
  • 没问题。无论如何,您能否提供一个计算 Scala 中时间戳差异的代码示例?
  • 工作台,你能做到吗?如果您可以分享sn-p,那将非常有帮助。谢谢
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-05-13
  • 1970-01-01
  • 2013-05-21
  • 2014-05-04
相关资源
最近更新 更多