我在MR作业的映射阶段中使用了一个自定义可写类作为VALUEOUT,其中类有两个字段A org.apache.hadoop.io.Text
和org.apache.hadoop.io.MapWritable
。在我的reduce函数中,遍历每个键的值,并执行两个操作:1. filter,2. aggregate。在过滤器中,我有一些规则来检查MapWritable中的某些值(键为Text
,值为IntWritable
或DoubleWritable
)是否满足某些条件,然后将其简单地添加到ArrayList中。在过滤操作结束时,我有一个过滤的自定义可写对象列表。在汇总阶段,当我访问这些对象时,结果是最后一个被成功过滤的对象已经覆盖了数组列表中的所有其他对象。在对最后一个对象覆盖所有其他对象的SO上列出了一些类似的问题之后,我确认了我没有静态字段,也没有通过设置不同的值来重复使用相同的自定义可写(这被引用为可能的原因)一个问题)。对于减速器中的每个键,我都确保CustomWritable
,Text
键和MapWritable
是新对象。另外,我还通过在我的reduce中删除了过滤器&聚合操作并刚刚迭代了这些值并使用for循环将它们添加到ArrayList中来执行简单测试。在循环中,每次我将一个CustomWritable添加到列表中时,我都记录了列表中所有内容的值。我在将元素添加到列表之前和之后进行了记录。这两个日志都表明前一组元素已被覆盖。我很困惑这种情况如何发生。一旦迭代值中的下一个元素被循环for (CustomWritable result : values)
访问,列表内容就被修改了。我无法弄清楚这种行为的原因。如果任何人都可以对此有所了解,这将非常有帮助。谢谢。迭代减速器中定制可写组件的问题
0
A
回答
1
reducer中的“values”迭代器在迭代时重用该值。这是一种用于性能和更小内存占用的技术。在幕后,Hadoop将下一条记录反序列化为同一个Java对象。如果你需要“记住”一个对象,你需要克隆它。
您可以利用Writable接口并使用原始字节来填充新对象。
IntWritable first = WritableUtils.clone(values.next(), context.getConfiguration());
IntWritable second = WritableUtils.clone(values.next(), context.getConfiguration());
+0
谢谢杰夫。像魅力一样工作。我想知道它是如何工作的,因为我们使用HBase org.apache.hadoop.hbase.client.Result作为值,因为它不是一个Writable类。尽管如此,我不记得遇到过这种Result对象的问题。 – KNP
相关问题
- 1. Hadoop的减速定制可写
- 2. 速度:迭代问题
- 3. 问题迭代器
- 4. 迭代器问题
- 5. 定制迭代器
- 6. 问题的迭代器
- 7. PHP数组迭代问题
- 8. 问题与组件迭代和验证
- 9. Javascript中的数组迭代问题
- 10. 在Swift中迭代数组的问题
- 11. 删除数组中迭代的问题
- 12. 为什么迭代元素数组乘法在numpy中减速?
- 13. C++“矢量迭代器不可递减”?
- 14. 快速迭代器
- 15. 你可以使用组合减速器组成深层状态减速器吗?
- 16. Spark(scala)问题迭代器
- 17. 迭代器实现问题
- 18. C++迭代器问题
- 19. 迭代器操作问题
- 20. C++,迭代器问题
- 21. C++迭代器问题
- 22. ServiceLoader双迭代器问题
- 23. JSF具有可定制内容的迭代复合组件
- 24. 减速机采用迭代错误
- 25. 这个减速器有什么问题
- 26. 编写二维数组的迭代器
- 27. C#文件迭代问题
- 28. JavaScript中的迭代问题
- 29. python中的迭代问题
- 30. 单元测试减速器,测试每个减速器或组合减速器?
我注意到这里有一个类似的问题:可迭代到ArrayList的元素改变(https://stackoverflow.com/questions/23329173/iterable-to-arraylist-elements-change?rq=1)。也许问题是相似的,但它有相同的值,不知道它是最后一个元素还是第一个访问的元素。即便如此,我有一个复杂的对象,每次都不得不重新创建一个新对象,这看起来像是一种笨拙和痛苦的选择,我不想诉诸于此。任何其他更好的选择? – KNP