flink的window

本文详细介绍了Apache Flink中的窗口机制,包括时间窗口、计数窗口、滑动窗口、滚动窗口、会话窗口和全局窗口等分类。窗口是处理无界数据流的关键,文章深入探讨了窗口的理解、分类、API、窗口分配器、窗口函数及其生命周期,并涉及测试水位线、处理迟到数据的方法。此外,还讲解了增量聚合和全窗口函数的结合使用,以及如何处理窗口的生命周期和迟到数据。
摘要由CSDN通过智能技术生成

|flink-1.9 docs:Apache Flink 1.9 Documentation: Windows

一、window的理解

1. Flink是一种流式计算引擎,用于处理无界数据流。在处理无界流时,一种有效的方式是将无限的数据切割成有限的"数据块",这就是窗口(Window)的概念。

2. 在Flink中,窗口是用来处理无界流的核心概念。你可以将窗口想象成一个动态创建的数据存储桶,数据源源不断地流入这些存储桶。当某个时间点窗口需要关闭时,它停止收集数据、触发计算并输出结果。

3. 窗口的时间范围以左闭右开的区间表示,例如,0~10秒的窗口表示为[0, 10)。

4. 在处理时间窗口时,窗口的关闭是基于系统时间的,即当数据的时间戳超过窗口结束时间时,窗口关闭并触发计算。对于迟到的数据,它们会被分配给后续窗口,但可能会导致处理结果不准确。

5. 在事件时间语义下,由于可能存在乱序数据,需要设置延迟时间来等待所有数据到达。这可以确保包含迟到的数据并保持准确性。

6. 窗口实际上可以被理解为多个有限大小的“存储桶”,数据会根据时间戳分发到对应的存储桶中。当到达窗口结束时间时,对每个存储桶中的数据进行计算处理。

7. 窗口是动态创建的,只有在有数据到达时才会创建对应的窗口。窗口的触发计算和关闭可以分开执行,确保数据被准确处理。

总之,Flink中的窗口是用来处理无界数据流的重要机制,通过动态创建存储桶和设置事件时间语义来确保数据的正确处理。

二、window的分类

窗口的分类可以按照不同的角度来进行划分:

1. 按照驱动类型分类

 1.1时间窗口(Time Window)

这种窗口根据时间段来截取数据。窗口的开始和结束由时间点定义,数据在这个时间段内进行收集和计算。时间窗口可以基于处理时间或事件时间定义。

1.2计数窗口(Count Window)

 这种窗口根据数据元素的个数来截取数据。当达到固定的数据个数时,窗口触发计算并关闭。计数窗口不依赖时间,只关注数据个数。

2. 按照窗口分配数据的规则分类

2.1滑动窗口(Sliding Window)

滑动窗口也有固定的大小,但窗口之间可以有一定的重叠。窗口的滑动步长决定了窗口的触发频率。数据可能同时属于多个窗口,取决于窗口大小和滑动步长的比值。

2.2 滚动窗口(Tumbling Window)

滚动窗口有固定的大小,窗口之间没有重叠,数据被均匀切片。数据属于一个窗口,无论何时,窗口之间没有间隔。

2.3 会话窗口(Session Window)

会话窗口基于数据之间的时间间隔来截取数据。如果数据之间的间隔小于指定的时间(会话超时时间),它们属于同一个会话窗口。会话窗口的长度是不固定的,可以根据数据的活动来动态划分。

2.4 全局窗口(Global Window)

全局窗口将相同键(key)的所有数据分配到一个窗口中,没有窗口结束的时间点。触发计算需要自定义触发器。这种窗口通常用于需要更灵活处理的情况,如计数窗口的底层实现就是全局窗口。

Flink中有多种窗口类型可供选择,可以根据不同的需求和数据特性来选择适当的窗口类型。每种窗口类型都有其特定的应用场景和用途。

三、窗口 DataStream api

|flink-1.9 docs:Apache Flink 1.9 Documentation: Windows

在Flink中,窗口操作主要分为按键分区窗口(Keyed Windows)和非按键分区窗口(Non-Keyed Windows),具体如下:

1. 按键分区窗口(Keyed Windows): 在按键分区窗口中,数据流通过.keyBy()操作被按键分区成多个逻辑流(KeyedStream),每个逻辑流都对应一个特定的键(key)。窗口计算会在多个并行子任务上同时执行,相同键的数据会被发送到同一个并行子任务上进行窗口计算。这意味着每个键都有一组独立的窗口进行统计计算。

在代码中,按键分区窗口操作的典型调用顺序如下:

//1、使用.keyBy()按键分区,将数据流按照键分成多个逻辑流。
stream.keyBy(<key selector>)
//2、使用.window()定义窗口,传入一个窗口分配器(Window Assigner),该分配器指定了窗口的类型和属性。
      .window(<window assigner>)
//3、使用.aggregate()或其他窗口函数定义窗口的处理逻辑
      .aggregate(<window function>)

2. 非按键分区窗口(Non-Keyed Windows): 如果没有进行.keyBy()按键分区,原始的DataStream不会分成多个逻辑流,窗口操作将在一个任务上执行,即并行度为1。一般情况下,不推荐使用非按键分区窗口,因为它无法充分利用并行性。

在代码中,非按键分区窗口操作的调用方式如下:

stream.windowAll(<window assigner>)
  • 直接使用.windowAll()定义窗口,传入一个窗口分配器,该分配器指定了窗口的类型和属性。
  • 需要注意的是,对于非按键分区窗口操作,手动调整窗口算子的并行度是无效的,因为windowAll本身是非并行操作。

总之,窗口操作需要先确定是按键分区窗口还是非按键分区窗口,然后根据需求使用相应的API调用来定义窗口分配器和窗口函数,以实现窗口计算。通常情况下,按键分区窗口更常见和有用,因为它能够更好地利用并行性。

四、窗口分配器(Window Assigners

|flink-1.9 docs:Apache Flink 1.9 Documentation: Windows

窗口分配器实际上是用于确定窗口类型的工具之一。

通常,最常见的定义方法是使用.window()方法,该方法需要传入一个WindowAssigner作为参数,并返回一个WindowedStream对象。

对于非按键分区窗口,可以直接使用.windowAll()方法,同样需要传入一个WindowAssigner,返回的是AllWindowedStream。

1、时间窗口

时间窗口是最常用的窗口类型,又可以细分为滚动、滑动和会话三种

1.1 滚动处理时间窗口
  • 使用TumblingProcessingTimeWindows.of()来定义,需要指定窗口的大小。
  • 例如:
    stream.keyBy(...)
       .window(TumblingProcessingTimeWindows.of(Time.seconds(5)))
       .aggregate(...);
    

使用场景:适用于周期性统计,比如每5秒钟计算一次统计数据。

1.2 滑动处理时间窗口
  • 使用SlidingProcessingTimeWindows.of()来定义,需要指定窗口的大小和滑动步长。
  • 例如:
    stream.keyBy(...)
       .window(SlidingProcessingTimeWindows.of(Time.seconds(10), Time.seconds(5)))
       .aggregate(...);
    

    使用场景:适用于连续统计,可以用于监控系统中的滚动平均值计算。

1.3处理时间会话窗口
  • 使用ProcessingTimeSessionWindows.withGap()或者.withDynamicGap()来定义,需要指定会话的超时时间或者动态提取会话超时时间的逻辑。
  • 例如:
    stream.keyBy(...)
       .window(ProcessingTimeSessionWindows.withGap(Time.seconds(10)))
       .aggregate(...);
    

    使用场景:用于处理连续的会话数据,例如用户在应用中的活动会话,会话之间的间隔超过一定时间会被视为不同的会话。

stream.keyBy(...)
   .window(ProcessingTimeSessionWindows.withDynamicGap(new SessionWindowTimeGapExtractor<Tuple2<String, Long>>() {
       @Override
       public long extract(Tuple2<String, Long> element) {
           // 提取session gap值返回, 单位毫秒
           return element.f0.length() * 1000;
       }
   }))
   .aggregate(...);
1.4 滚动事件时间窗口
  • 类似于滚动处理时间窗口,使用TumblingEventTimeWindows.of()来定义。
  • 例如:
    stream.keyBy(...)
       .window(TumblingEventTimeWindows.of(Time.seconds(5)))
       .aggregate(...);
    

    场景:适用于处理数据流中的事件,例如实时日志分析、事件时间的流式处理等。

1.5滑动事件时间窗口
  • 类似于滑动处理时间窗口,使用SlidingEventTimeWindows.of()来定义。
  • 例如:
    stream.keyBy(...)
       .windo
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值