窗口触发的条件 : 水位线 >= 窗口结束的时间
一
不分组,按照EventTime划分滚动窗口
Non-keyed Window,底层调用的是windowAll
public class EventTimeTumblingWindowAllDemo {
public static void main(String[] args) throws Exception {
// 2021-03-06 21:00:00,1
// 2021-03-06 21:00:05,2
// 结果 : 2> 1
// 3> 2
StreamExecutionEnvironment env = StreamExecutionEnvironment.createLocalEnvironmentWithWebUI(new Configuration());
// 老版本必须要设置时间标准 (1.20 之前的)
env.setStreamTimeCharacteristic(TimeCharacteristic.EventTime);
DataStreamSource<String> lines = env.socketTextStream("linux01", 8888);
// flink里面的时间都精确到毫秒
// 时间提取器 BoundedOutOfOrdernessTimestampExtractor : 允许时间乱序,并且可以指定窗口延时
// WaterMark (水位线,可以让窗口延迟触发的一种机制)
// 一个窗口中的一个分区的水位线 = 当前窗口当前分区最大的 EventTime - 延迟时间 Time.seconds(0)
SingleOutputStreamOperator<String> linesWithWaterMark = lines.assignTimestampsAndWatermarks(new BoundedOutOfOrdernessTimestampExtractor<String>(Time.seconds(0)) {
private SimpleDateFormat dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss") ;
@Override
public long extractTimestamp(String s) {
String strings = s.split(",")[0];
long timestamp = 0;
try {
Date date = dateFormat.parse(strings);
timestamp = date.getTime();
} catch (ParseException e) {
e.printStackTrace();
timestamp = System.currentTimeMillis();
}
return timestamp;
}
});
SingleOutputStreamOperator<Integer> nums = linesWithWaterMark.map(new MapFunction<String, Integer>() {
@Override
public Integer map(String s) throws Exception {
int i = Integer.parseInt(s.split(",")[1]);
return i;
}
});
// 划分窗口
AllWindowedStream<Integer, TimeWindow> window = nums.windowAll(TumblingProcessingTimeWindows.of(Time.seconds(5)));
// 对 window 中的数据 进行聚合
SingleOutputStreamOperator<Integer> sum = window.sum(0);
sum.print();
env.execute() ;
}e
}
先分组 然后 根据 EventTime 划分 滚动窗口
keyed Window
底层调用的是window ,传入对应的 winodw Assinger
public class EventTimeSlidingWindowDemo {
public static void main(String[] args) throws Exception {
StreamExecutionEnvironment env = StreamExecutionEnvironment.createLocalEnvironmentWithWebUI(new Configuration());
// 两秒 调一次方法
env.getConfig().setAutoWatermarkInterval(1000);
// 老版本必须要设置时间标准 (1.20 之前的)
env.setStreamTimeCharacteristic(TimeCharacteristic.EventTime);
DataStreamSource<String> lines = env.socketTextStream("linux01", 8888);
// flink里面的时间都精确到毫秒
// 时间提取器 BoundedOutOfOrdernessTimestampExtractor : 允许时间乱序,并且可以指定窗口延时
// WaterMark (水位线,可以让窗口延迟触发的一种机制)
// 一个窗口中的一个分区的水位线 = 当前窗口当前分区最大的 EventTime - 延迟时间 Time.seconds(0)
SingleOutputStreamOperator<String> linesWithWaterMark = lines.assignTimestampsAndWatermarks(new BoundedOutOfOrdernessTimestampExtractor<String>(Time.seconds(0)) {
@Override
public long extractTimestamp(String s) {
return Long.parseLong(s.split(",")[0]); // EventTime
}
});
// 提取完 EventTime 后生成 WaterMark ,但数据还是原来的老样子
// 1000,spark,1 --> spark,1
SingleOutputStreamOperator <Tuple2<String,Integer>> WordAndCount = linesWithWaterMark.map(new MapFunction<String, Tuple2<String,Integer>>() {
@Override
public Tuple2<String,Integer> map(String s) throws Exception {
String[] split = s.split(",");
return Tuple2.of(split[1],Integer.parseInt(split[2]));
}
});
// 先 keyBy,再划分窗口
KeyedStream<Tuple2<String, Integer>, String> keyed = WordAndCount.keyBy(t -> t.f0);
// 划分窗口
WindowedStream<Tuple2<String, Integer>, String, TimeWindow> window = keyed.window(SlidingEventTimeWindows.of(Time.seconds(10), Time.seconds(5)));
// 对窗口里面的数据进行 sum
SingleOutputStreamOperator<Tuple2<String, Integer>> sum = window.sum(1);
sum.print();
env.execute() ;
}
}