Flink Streaming Python API-reduce()产生增量结果,而不是最终值

时间:2019-05-13 12:49:52

标签: python apache-flink flink-streaming

我正在尝试使用Python API进行流式传输在Flink上实现Kmeans Cluctering算法。我正在根据第0个索引进行key_by,然后尝试在每个组上reduce()进行计数汇总。

class CentroidAccumulator(ReduceFunction):                                                                                                                                       
    def reduce(self, val1, val2):                                                                                                                                                
        id1, point1, count1 =  val1                                                                                                                                              
        id2, point2, count2 =  val2                                                                                                                                              
        return (id1, point1.add(point2), count1+count2)   

class Selector(KeySelector):                                                                                                                                                     
    def getKey(self, value):                                                                                                                                                     
        return value[0]   


nearest_points = points \                                                                                                                                                
                .map(SelectNearestPoint(centroids)) \                                                                                                                            
                .key_by(Selector()).reduce(CentroidAccumulator()) 
nearest_points.write_as_text("output.txt")

预期结果:

(1, <tuple>, count)
(2, <tuple>, count)
(3, <tuple>, count)
(4, <tuple>, count)

实际结果:

我将所有迭代的输出写入文件中(我要测试的样本中有40个点,因此输出有40行,就像这样)

(1, <kmeans_clustering.Point instance at 0x2>, 1)                                                                                                                                
(3, <kmeans_clustering.Point instance at 0x3>, 1)                                                                                                                                
(2, <kmeans_clustering.Point instance at 0x4>, 1)                                                                                                                                
(2, <kmeans_clustering.Point instance at 0x5>, 2)                                                                                                                                
.
.
.                                                                                                                
(2, <kmeans_clustering.Point instance at 0x20>, 13)                                                                                                                              
(2, <kmeans_clustering.Point instance at 0x21>, 14)                                                                                                                              
(1, <kmeans_clustering.Point instance at 0x22>, 10)                                                                                                                              
(4, <kmeans_clustering.Point instance at 0x23>, 4)                                                                                                                               
(2, <kmeans_clustering.Point instance at 0x24>, 15)                                                                                                                              
(2, <kmeans_clustering.Point instance at 0x25>, 16)                                                                                                                              
(1, <kmeans_clustering.Point instance at 0x26>, 11)                                                                                                                              
(4, <kmeans_clustering.Point instance at 0x27>, 5)                                                                                                                               
(2, <kmeans_clustering.Point instance at 0x28>, 17)                                                                                                                              
(2, <kmeans_clustering.Point instance at 0x29>, 18) 

问题是好的还原,但是我只想获取每个组的reduce转换的最后一个值(这是我应该理解的reduce的工作方式)。我在做什么错了?

1 个答案:

答案 0 :(得分:1)

您没有做错任何事;这是流式缩减功能的预期行为。从概念上讲,数据流是无穷无尽的数据流-因此“等到最后”才能产生结果没有意义。流式传输程序的标准行为是为每个事件生成结果。

当然,这可能会带来一些不便。如果您只想查看最终结果,则必须使用某种方法来指示结束。使用批处理程序,这自然而然。在流应用程序中,有限的数据源会发送带有值MAX_WATERMARK的水印,该水印可用于检测输入是否已到达末尾-您可以使用事件时间计时器将其捕获到ProcessFunction中,但这是一个复杂的解决方案。您还可以使用Windows来实现某种解决方法。