我正在尝试为hadoop设计一个Map器和缩减器。我是hadoop的新手,对于Map器和还原器应该如何为我的特定应用程序工作,我有点困惑。
Map器的输入是一个大的有向图的连通性。它是一个2列输入,其中每行是一个单独的边连接。第一列是每个边的开始节点id,第二列是结束节点id。我试图将每个开始节点id的邻居数输出到一个2列文本文件中,其中第一列按开始节点id的增加顺序排序。
我的问题是:
(1) 输入已经设置为每一行都是一个键-值对,其中键是开始节点id,值是结束节点id。Map程序是否只需读入每一行并将其写出?这似乎是多余的。
(2) 排序是在Map器和reducer之间进行的,还是可以用reducer本身进行排序?
1条答案
按热度按时间wnvonmuf1#
如果我的理解是正确的,您需要计算一个键将有多少个不同的值。
简单地在Map器中发出输入键-值对,然后在reducer中计算每个键的不同值(例如,将它们添加到一个集合中,并将集合大小作为reducer的值发出),这是一种方法,但正如您所说,有点多余。
一般来说,您希望减少网络通信量,因此您可能希望在洗牌之前进行更多的计算(是的,这是由hadoop完成的)。
提高效率的两种简单方法是:
1) 使用组合器,它将输出一组值,而不是单个值。这样,您将向还原器发送更少的键值对,而且,一些值可能会被跳过,因为它们已经在同一个键的本地值集中。
2) 使用Map端聚合。与其立即发出输入键值对,不如将它们本地存储在数据结构(如hashmap或multimap)中的Map器(内存中)。键可以是map输入键,值可以是迄今为止看到的该键的一组值。每遇到一种类型,都会为该键添加一个新值,然后将其附加到此结构中。在每个Map器的末尾,从close()方法(如果我记得名称的话)发出这个结构(或者将值转换为数组)。
您可以使用关键字“combiner”和“map side aggregation”来查找这两种方法。
对键进行全局排序有点棘手。再说一次,有两个基本的选项,但不是很好:1)使用一个reducer,但是并行性没有任何好处;2)使用total order partitioner,这需要一些额外的编码。
除此之外,您可能希望转到spark以获得更直观、更高效的解决方案。