对值进行两次迭代(MapReduce)
我收到一个迭代器作为参数,并且想对值进行两次迭代。
public void reduce(Pair<String,String> key, Iterator<IntWritable> values, Context context)
可能吗 ?怎么样 ?签名是由我使用的框架(即Hadoop)强加的。
-编辑-
最后,该reduce
方法的真正签名是一个iterable
。我被这个Wiki页面所迷住了(实际上这是我发现的唯一不被弃用(但错误的)单词计数示例)。
回答:
如果要再次迭代,我们必须缓存来自迭代器的值。至少我们可以将第一次迭代和缓存结合起来:
Iterator<IntWritable> it = getIterator();List<IntWritable> cache = new ArrayList<IntWritable>();
// first loop and caching
while (it.hasNext()) {
IntWritable value = it.next();
doSomethingWithValue();
cache.add(value);
}
// second loop
for(IntWritable value:cache) {
doSomethingElseThatCantBeDoneInFirstLoop(value);
}
(只需要添加代码答案,就知道您在自己的注释中提到了该解决方案;))
为什么 不进行缓存就不可能做到:
为什么Iterator
是实现接口的Iterator
对象,并且没有一个唯一的要求,即对象实际上存储值。进行两次迭代,您必须重置迭代器(不可能)或克隆它(再次:不可能)。
举一个克隆/重置毫无意义的迭代器为例:
public class Randoms implements Iterator<Double> { private int counter = 10;
@Override
public boolean hasNext() {
return counter > 0;
}
@Override
public boolean next() {
count--;
return Math.random();
}
@Override
public boolean remove() {
throw new UnsupportedOperationException("delete not supported");
}
}
以上是 对值进行两次迭代(MapReduce) 的全部内容, 来源链接: utcz.com/qa/418701.html