如何优化这个MapReduce函数,Python,mrjob

时间:2013-04-05 20:29:20

标签: python hadoop mapreduce mrjob

我是Map / Reduce原理和python mrjob框架的新手,我编写了这个示例代码,它工作正常,但我想知道我可以改变它以使其“完美”/更高效

from mrjob.job import MRJob
import operator
import re

# append result from each reducer 
output_words = []

class MRSudo(MRJob):

    def init_mapper(self):
        # move list of tuples across mapper
        self.words = []

    def mapper(self, _, line):
        command = line.split()[-1]
        self.words.append((command, 1))

    def final_mapper(self):
    for word_pair in self.words:
            yield word_pair

    def reducer(self, command, count): 
        # append tuples to the list
        output_words.append((command, sum(count)))

    def final_reducer(self):
        # Sort tuples in the list by occurence
        map(operator.itemgetter(1), output_words)
        sorted_words = sorted(output_words, key=operator.itemgetter(1), reverse=True)
        for result in sorted_words:
            yield result

    def steps(self):
        return [self.mr(mapper_init=self.init_mapper,
                        mapper=self.mapper,
                        mapper_final=self.final_mapper,
                        reducer=self.reducer,
                        reducer_final=self.final_reducer)]

if __name__ == '__main__':
    MRSudo.run()

1 个答案:

答案 0 :(得分:4)

有两种方法可以遵循。

<强> 1。改善您的流程

您正在进行分布式字数统计。此操作是代数的,但您没有利用此属性。

对于输入的每个单词,您都要向减速器发送记录。必须对这些字节进行分区,通过网络发送,然后由reducer进行排序。它既不高效也不可扩展,映射器向减速器发送的数据量通常是一个瓶颈。

您应该为工作添加一个组合器。它将与您当前的减速器完全相同。组合器在映射器之后运行在同一地址空间中。这意味着您通过网络发送的数据量不再与输入的字数呈线性关系,而是受唯一字数量的限制。这通常要低几个数量级。

由于分布式字数统计示例被过度使用,您可以通过搜索“分布式字数统计器”轻松找到更多信息。所有代数运算都必须有一个组合器。

<强> 2。使用更有效的工具

Mrjob是快速编写地图减少工作的好工具。通常,编写python Job比使用Java更快。但是它有运行时成本:

  1. Python通常比Java慢
  2. MRJob比大多数python框架慢,因为它还没有使用typedbytes
  3. 您必须决定是否值得使用常规API重写Java中的一些作业。如果您正在编写长期批处理作业,那么投入一些开发时间来降低运行时成本是有意义的。

    从长远来看,编写Java Job通常不会比在python中编写它更长。但是你必须做一些前期投资:用构建系统创建一个项目,打包它,部署它等。使用MRJob你只需要执行你的python文本文件。

    几个月前Cloudera做了benchmark of the Hadoop python frameworks。 MRJob比他们的Java工作慢5到7倍。当typedbytes可用时,MRJob的表现应该会提高,但Java工作的速度仍然会快2至3倍。