四、【计算】流计算中的Window计算(中) | 青训营笔记

简介: 四、【计算】流计算中的Window计算(中) | 青训营笔记

👉引言💎


学习的最大理由是想摆脱平庸,早一天就多一份人生的精彩;迟一天就多一天平庸的困扰。 热爱写作,愿意让自己成为更好的人............

铭记于心
🎉✨🎉我唯一知道的,便是我一无所知🎉✨🎉


三、Window


1 概述:


  • 内容涵盖:
  1. window的基本概念、分类、以及三种最常见的window的功能;同时也会讲解使用window的时候的一些典型的问题;
  2. window中涉及到的一些高级的优化及其实现原理
  • Window分类:典型Window:
  1. Tumble Window(滚动)
  2. Sliding Window(滑动)
  3. Session Window(会话)
  • 其他:
  1. 全局Window
  2. Count  Window
  3. 累计窗口
  • 使用:

image.png


2 TUMBLE Window (滚动窗口)


这是最常见的窗口类型,就是根据数据的时间(可以是处理时间,也可以是事件时间)划分到它所属的窗口中windowStart = timestamp - timestamp % windowSize,这条数据所属的window就是[windowStart, windowStart + windowSize)

在我们使用window的过程中,最容易产生的一个疑问是,window的划分是subtask级别的,还是key级别的。这里大家要记住,Flink 中的窗口划分是key级别的。 比如下方的图中,有三个key,那每个key的窗口都是单独的。所以整个图中,一种存在14个窗口。

窗口的触发,是时间大于等于window end的时候,触发对应的window的输出(计算有可能提前就增量计算好了),目前的实现是给每个window都注册一个timer,通过处理时间或者事件时间的timer来触发window的输出。

image.png


3 HOP Window (滑动窗口)


了解了上面的TUMBLE窗口的基本原理后,HOP窗口就容易理解了。上面的TUMBLE窗口是每条数据只会落在一个窗口中。在HOP窗口中,每条数据是可能会属于多个窗口的(具体属于多少,取决于窗口定义的大小和滑动),比如下图中假设滑动是1h的话,那窗口大小就是2h,这种情况每条数据会属于两个窗口。除了这一点之外,其它的基本跟HOP窗口是类似的,比如也是key级别划分窗口,也是靠timer进行窗口触发输出。

image.png


4 Session Window (会话窗口)


会话窗口跟上面两种窗口区别比较大,上面两个窗口的划分,都是根据当前数据的时间就可以直接确定它所属的窗口。会话窗口的话,是一个动态merge的过程。一般会设置一个会话的最大的gap,比如10min。

那某个key下面来第一条数据的时候,它的window就是 [event_time, event_time + gap),当这个key后面来了另一条数据的时候,它会立即产生一个窗口,如果这个窗口跟之前的窗口有overlap的话,则会将两个窗口进行一个merge,变成一个更大的窗口,此时需要将之前定义的timer取消,再注册一个新的timer。

所以会话窗口要求所有的聚合函数都必须有实现merge

image.png


5 迟到数据处理


  • 定义迟到
    watermark驱动某个窗口触发输出后,这个窗口如果后面又来了数据,则为迟到数据(注意,不是数据的时间晚于watermark就算是迟到,而是它所属的窗口已经被触发了,才算迟到)
    即: 一条数据到来后,会用WindowAssigner给它划分一个window,一般时间窗口是一个时间区间,比如[10:00, 11:00),如果划分出来的window end 比当前的watermark值还小,说明这个窗口已经触发了计算了,这条数据会被认为是迟到数据。
  • 只有事件时间 下才会有迟到的数据
  • 对于迟到的数据,我们现在有两种处理方式:image.png
  • Allow lateness
    这种方式需要设置一个允许迟到的时间,设置之后,窗口正常计算结束后,不会马上清理状态,而是会多保留allowLateness这么长时间,在这段时间内如果还有数据到来,则继续之前的状态进行计算。
  • SideOutput
    这种方式需要对迟到数据打一个tag,然后在DataStream上根据这个tag获取到迟到数据流,然后业务层面自行选择进行处理
  • 注意:side output只有在DataStream的窗口中才可以用,在SQL中目前还没有这种语义,所以暂时只有drop这一个策略。


6 增量计算 VS 全量计算


这个问题也是使用窗口的时候最典型的问题之一。先定义一下:

  • 增量计算:每条数据到来后,直接参与计算(但是还不需要输出结果)

image.png

  • 全量计算:每条数据到来后,先放到一个buffer中,这个buffer会存储到状态里,直到窗口触发输出的时候,才把所有数据拿出来统一进行计算

image.png

在SQL里面,主要是窗口聚合,所以都是可以增量计算的,也就是每条数据来了之后都可以直接进行计算,而不用把数据都存储起来。举个例子,比如要做sum计算,那每来一条数据,就直接把新的数据加到之前的sum值上即可,这样我们就只需要存储一个sum值的状态,而不需要存储所有buffer的数据,状态量会小很多。

DataStream里面要用增量计算的话,需要用reduce/aggregate等方法,就可以用到增量计算。如果用的是process接口,这种就属于是全量计算。


7 EMIT触发


上面讲到,正常的窗口都是窗口结束的时候才会进行输出,比如一个1天的窗口,只有到每天结束的时候,窗口的结果才会输出。这种情况下就失去了实时计算的意义了.

那么EMIT触发就是在这种情况下,可以提前把窗口内容输出出来的一种机制。比如我们可以配置一个1天的窗口,每隔5s输出一次它的最新结果,那这样下游就可以更快的获取到窗口计算的结果了.

这个功能只在SQL中,如果是在DataStream中需要完成类似的功能,需要自己定义一些trigger来做.

上节课中,有讲到retract机制,这里需要提一下,这种emit的场景就是一个典型的retract的场景,发送的结果类似于+[1], -[1], +[2], -[2], +[4]这样子。这样才能保证window的输出的最终结果是符合语义的。


8 Window Offset


按照上面提到的,滚动窗口的计算方式是:windowStart = timestamp - timestamp % windowSize [windowStart, windowStart + windowSize),这个时间戳是按照unix timestamp来算的。比如我们要用一个一周的窗口,想要的是从周一开始,到周日结束,但是按照上面这种方式计算出来的窗口的话,就是从周四开始的(因为1970年1月1日是周四)。

那么window offset的功能就是可以在计算窗口的时候,可以让窗口有一个偏移。所以最终计算window的公式就变成了:windowStart = timestamp - (timestamp - offset + windowSize) % windowSize

DataStream原生就是支持offset的,但是SQL里并不支持,字节内部版本扩展支持了SQL的window offset功能


9 总结


  1. 三种(滚动、滑动、会话)窗口的定义
  2. 迟到数据处理: AllowLateness, SideOutput
  3. 增量计算和全量计算模型
  4. EMIT触发提前输出窗口的结果

🌹写在最后💖: 路漫漫其修远兮,吾将上下而求索!伙伴们,再见!🌹🌹🌹


相关文章
|
2月前
|
消息中间件 SQL Apache
实时计算 Flink版产品使用合集之想要解决RangeMap在处理重叠范围时的裁开问题如何解决
实时计算Flink版作为一种强大的流处理和批处理统一的计算框架,广泛应用于各种需要实时数据处理和分析的场景。实时计算Flink版通常结合SQL接口、DataStream API、以及与上下游数据源和存储系统的丰富连接器,提供了一套全面的解决方案,以应对各种实时计算需求。其低延迟、高吞吐、容错性强的特点,使其成为众多企业和组织实时数据处理首选的技术平台。以下是实时计算Flink版的一些典型使用合集。
|
SQL 分布式计算 大数据
四、【计算】流计算中的Window计算(上) - 青训营笔记
四、【计算】流计算中的Window计算(上) - 青训营笔记
四、【计算】流计算中的Window计算(上) - 青训营笔记
|
SQL 存储 资源调度
四、【计算】流计算中的Window计算(下) | 青训营笔记
四、【计算】流计算中的Window计算(下) | 青训营笔记
四、【计算】流计算中的Window计算(下) | 青训营笔记
|
SQL 存储 Unix
流式计算中的 Window 计算|青训营笔记
介绍实时计算中的Watermark概念,以及如何产生、传递,还有一些典型的生产实践中遇到的问题;介绍三种最基本的window类型,以及他们的实现原理;同时会结合业务场景介绍一些高级优化的功能和原理
198 0
流式计算中的 Window 计算|青训营笔记
|
存储 分布式计算 大数据
二、【计算】流|批|OLAP一体 的Fllink引擎 (上)| 青训营笔记
二、【计算】流|批|OLAP一体 的Fllink引擎 (上)| 青训营笔记
二、【计算】流|批|OLAP一体 的Fllink引擎 (上)| 青训营笔记
|
SQL 分布式计算 大数据
七、【计算】Presto架构原理与优化介绍(上) | 青训营笔记
七、【计算】Presto架构原理与优化介绍(上) | 青训营笔记
七、【计算】Presto架构原理与优化介绍(上) | 青训营笔记
|
存储 SQL 算法
三、【计算】Exactly Once 语义在Flink中的实现(上) | 青训营笔记
三、【计算】Exactly Once 语义在Flink中的实现(上) | 青训营笔记
三、【计算】Exactly Once 语义在Flink中的实现(上) | 青训营笔记
|
存储 消息中间件 关系型数据库
三、【计算】Exactly Once 语义在Flink中的实现(下) | 青训营笔记
三、【计算】Exactly Once 语义在Flink中的实现(下) | 青训营笔记
三、【计算】Exactly Once 语义在Flink中的实现(下) | 青训营笔记
|
SQL 运维 OLAP
二、【计算】流|批|OLAP一体 的Flink引擎(下) | 青训营笔记
二、【计算】流|批|OLAP一体 的Flink引擎(下) | 青训营笔记
二、【计算】流|批|OLAP一体 的Flink引擎(下) | 青训营笔记
|
存储 分布式计算 大数据
六、【计算】大数据Shuffle原理与实践(下) | 青训营笔记
六、【计算】大数据Shuffle原理与实践(下) | 青训营笔记
六、【计算】大数据Shuffle原理与实践(下) | 青训营笔记