繁体   English   中英

返回调用者时,apache Beam中的flatmap对输入pcollection到底有什么作用?

[英]What does flatmap in apache beam exactly do to the input pcollection when returning to the caller?

我使用的Apache光束2.10,并试图了解究竟flatmap被返回pcollection给调用者的时候做。

阅读在线文档中的解释后,我认为flatMap可以像示例一样将PCollection元素集合简单地拆分为单个pcollection。

可调用对象必须为输入PCollection的每个元素返回一个可迭代的对象。 这些可迭代对象的元素将被展平到输出PCollection中。

但是在以下代码的情况下, flatMap展平“ Hello World”的每个字符,而不是整体返回“ Hello World”。

def simple(x):
    logging.info("Inside simple type: {0}, val: {1}".format(type(x), x))

    # Just return
    return x

def run():
    with beam.Pipeline(runner='DirectRunner') as p:
        elems = p | 'map:init' >> beam.Create(["Hello World"])

        #
        # Sample with FlatMap
        #
        ( elems | 'flatmap:exec'   >> beam.FlatMap(simple) # 1 to 1 relation with flatmap
            | 'flatmap:out'    >> beam.io.textio.WriteToText(file_path_prefix='flatmap')
        )

def main():
    run()

if __name__ == "__main__":
  main()

结果

H
e
l
l
o

W
o
r
l
d

但是,当我返回一个生成器时 ,就像下面的代码一样,迭代的结果似乎变成了pcollection。

def simple(x):
    logging.info("Inside simple type: {0}, val: {1}".format(type(x), x))

    # Just return
    yield x

def run():
    with beam.Pipeline(runner='DirectRunner') as p:
        elems = p | 'map:init' >> beam.Create(["Hello World"])

        #
        # Sample with FlatMap
        #
        ( elems | 'flatmap:exec'   >> beam.FlatMap(simple) # 1 to 1 relation with flatmap
            | 'flatmap:out'    >> beam.io.textio.WriteToText(file_path_prefix='flatmap')
        )

def main():
    run()

if __name__ == "__main__":
  main()

结果

Hello World

新增时间:2019年5月2日JST

如果我从字面上返回一个迭代器,则将迭代一个字符串,并将每个字符展平为PCollections。

def simple(x):
    logging.info("Inside simple type: {0}, val: {1}".format(type(x), x))

    # Just return
    return iter(x)

def run():
    with beam.Pipeline(runner='DirectRunner') as p:
        elems = p | 'map:init' >> beam.Create(["Hello World"])

        #
        # Sample with Map
        #
        ( elems | 'flatmap:exec'   >> beam.FlatMap(simple) # 1 to 1 relation with flatmap
            | 'flatmap:out'    >> beam.io.textio.WriteToText(file_path_prefix='flatmap')
        )

def main():
    run()

if __name__ == "__main__":
  main()

结果

H
e
l
l
o

W
o
r
l
d

那么,在将PCollection返回给调用者函数时,flatMap到底能做什么?

FlatMap假定给定函数的返回类型是iterable 在第一个示例中, simple返回"Hello World" 作为iterable"Hello World"可以被视为['H','e','l','l','o',' ','W','o','r','l','d'] 因此,第一个示例的工作方式如下:

  1. [] -> create -> ["Hello World"]
  2. ["Hello World"] -> map -> [['H','e','l','l','o',' ','W','o','r','l','d']]
  3. [['H','e','l','l','o',' ','W','o','r','l','d']] -> flatten -> ['H','e','l','l','o',' ','W','o','r','l','d']

最终PCollection: ['H','e','l','l','o',' ','W','o','r','l','d']

但是,在第二个示例中, simple得出x 您可以认为simple返回包含单个元素x iterator 因此,您的第二个示例是这样的:

  1. [] -> create -> ["Hello World"]
  2. ["Hello World"] -> map -> [["Hello World"]]
  3. [["Hello World"]] -> flatten -> ["Hello World"]

最终PCollection: ["Hello World"]

要回答您的最后一个问题:

yield xreturn iter(x)在语义上是不同的。 以下示例可以帮助您理解上下文。

>>> list(iter("abc"))
['a', 'b', 'c']
>>> def x(): yield "abc"
>>> list(x())
['abc']

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM