在本文中,我将分享编码示例,这些示例是 Flink 中 TumblingWindow 的一些关键方面。不熟悉 Flink 流的人员可以在此处获得介绍。
在进入TumblingWindow之前,让我们在流处理或流计算方面对”窗口”有一个基本的了解。 在数据流中,您有一个源持续生成数据,这使得计算最终值变得不可行。
在大多数用例中,要获得有意义的信息,最好使用两种方法
- 随时间的有限集计算(例如,每分钟 HTTP 401 错误)
- 计算以滚动更新完成(例如,记分板、趋势主题)
“Window”定义一组有限的元素,用于未绑定的流,我们可以应用计算。此集可以基于时间、元素计数、计数和时间的组合,或者一些自定义逻辑来将元素分配给窗口。
- 每分钟收到的订单数(固定时间)
- 完成最后 100 个订单的平均时间(固定元素)
流式处理框架供应商实现如何定义”窗口”的多个变体。Flink 有三种类型(a) 翻滚 (b) 滑动和 (c) 会话窗口,我将集中讨论本文的第一个窗口。
您还可以享受:带Apache Flink 的流式 ETL
翻滚窗口
这个窗口简单易懂,易于入门。它是一个固定大小的窗口,其中”大小”是时间(30 秒,5 分钟)或只是计数(100 个元素)。
5 分钟的时间窗口将收集到达窗口中的所有元素,并在 5 分钟后对其进行评估计数窗口100 将在窗口中收集 100 个元素,并在添加第 100 个元素后计算该窗口。
最重要的是,不会重叠窗口,也不会有重复的元素。每个元素仅分配给一个窗口。如果已指定密钥,则 Flink 将在逻辑上对流进行分区,并为每个键控元素运行并行窗口操作。
让我们举一个例子来更好地理解它们。一个简单的 IntegerGenerator
“”类充当源,每秒生成一个整数(从 1 开始)。以下行初始化本地 Flink 环境并创建 DataStream 对象。
流执行环境env=流执行环境。获取执行环境();
数据流<整数>intStream=env
时间窗口ALL(时间.秒( 5 )
.进程(新进程AllWindow函数_lt;整数,整数,时间窗口>()
{
@Override
公共 void 进程(上下文 arg0、可迭代<整数>输入、收集器_lt;整数>输出)引发异常
{
logger.info(”计算对 _}的计算总和”,输入 );
int 总和 = 0;
for (int i : 输入) |
总和 = i;
}
输出.收集(总和 );
}
})
.print();
env.execute();
xxxxxxxxx
intStream
.时间窗口所有时间。秒5 )
信息(”计算总和”,输入);
int总和=0;
(inti输入) |
总和=i;
}
输出。收集总和;
}
})
.印刷();
Env
在这里,我只是计算在给定窗口期间收集的所有整数的总和。
注意– ProcessAllWindowFunction
将允许 Flink 缓冲内存中窗口的所有元素,然后传递整个元素进行计算。因此,将 Iterable<>
对象作为 输入参数。 process()
第 13 行 – 将此窗口的结果返回 Flink,以便执行下一步,即在控制台上打印。
以下显示示例运行的输出
让我们在这里剖析输出。
- 行#1 – #3 = 在当前窗口关闭之前生成了两个整数。请注意,即使我们说五秒钟,第一个窗口没有运行五秒钟。原因是,默认情况下 Flink 会舍入到最近的时钟边界,在我们的案例中,该边界发生在”13:33:55″。这触发了 Flink 触发器窗口以关闭当前窗口并将其传递到下一步(Flink 的运算符)。
- 行#4 = 使用
process()
所有元素调用方法 [1, 2],总和 “3”打印到控制台 - 行#5 – #10 = 新窗口开始,并收集下一组整数。在”13:34:00″5秒后,窗口关闭。所收集的所有数据都发送到处理,其中打印它收到的整数,并计算此窗口中的数字总和 = “18”。
- 行#11 = 当前窗口总和打印到控制台。
- 类似的逻辑从线#12进一步应用。
备注 –此新窗口中不存在上一个窗口中的整数。下一个窗口在当前窗口关闭后启动(没有重叠和重复)。
翻滚计数窗口
执行();
X
intStream
.计数窗口所有4 )
.减少新的减少函数<整数>()
{
公共整数减少整数值1整数值2引发异常
{
记录
印刷();
env.执行();
使用与 IntegerGenerator
源相同的,上面是计数窗口的示例
第 2 行 = 定义由四个元素组成的翻转窗口(按计数确定大小)
第 3 行 = 使用 Flink 的”缩减功能”API 定义要对窗口元素执行的计算。逻辑是相同的(数字之和)
备注 – ReduceFunction
将允许 Flink 执行增量计算(滚动更新)。与进程功能相比,内存占用量非常少。第一个参数是上一个窗口的计算值,第二个参数是分配给此窗口的当前元素。
第 4 行 = 将此窗口的最终结果打印到控制台。
下面显示了示例运行的输出:
让我们在这里了解输出
- 行#1 – #3 = 收集前两个整数,然后 Flink 触发触发器窗口,使用前两个元素调用 reduce() 方法。 计算值”3″在 Flink 中缓冲
- 行#4 = 下一个整数值”3″由源生成。
- 行#5 =
reduce()
方法调用,请注意在这里的第一个参数是’3’从上一个计算和第二个参数是源生成的当前整数
reduce()
方法调用第一个参数为”6″,第二个参数称为”4″。计算值现在为 10。此时,Flink 从源收集了 4 个整数,因此,此窗口的计数条件已得到满足。reduce()
使用一组新的数字调用,现在为5和6类似的逻辑应用于接下来的两个数字,并 reduce()
相应地调用以执行增量更新。
线路#16 = 当 Flink 获取当前窗口的 4 个号码时,它会调用 print()
并输出 26(5+6+7+8)
结论
在本文中,我们观察了两种类型的 TumblingWindow(时间与计数)及其默认行为。我们还看到了两个窗口函数,ProcessAll 函数和用于累积和增量计算的函数函数。
在下一部分中,我将分享并讨论如何重写某些默认行为,以及如何处理延迟到达数据的问题。
进一步阅读