【问题标题】:Multiple Custom Writable formats多种自定义可写格式
【发布时间】:2012-05-04 21:57:02
【问题描述】:

我有多个输入源,我使用 Sqoop 的 codegen 工具为每个输入源生成自定义类

public class SQOOP_REC1 extends SqoopRecord  implements DBWritable, Writable

public class SQOOP_REC2 extends SqoopRecord  implements DBWritable, Writable

在 Map 端,根据输入源,我相应地创建了上述 2 个类的对象。

我的键类型为“文本”,因为我有两种不同类型的值,所以我将值输出类型保持为“可写”。

在 reduce 方面,我接受值类型为 Writable。

   public class SkeletonReduce extends Reducer<Text,Writable, Text, Text> {

public void reduce(Text key, Iterable<Writable> values, Context context) throws     IOException,InterruptedException {

   }
}

我也设置了

job.setMapOutputValueClass(Writable.class);

在执行过程中,根本不进入reduce函数。

有人可以告诉我是否可以这样做吗?如果是这样,我做错了什么?

【问题讨论】:

    标签: hadoop writable


    【解决方案1】:

    您不能将Writable 指定为您的输出类型;它必须是一个具体的类型。在Mappers 和Reducers 中,所有记录都需要具有相同的(具体)键和值类型。如果您需要不同的类型,您可以创建某种混合Writable,其中包含“A”或“B”。它有点难看,但很有效,例如在 Mahout 中做了很多。

    但我不知道为什么这会使减速器无法运行;这很可能是完全不同的事情,根据这些信息无法回答。

    【讨论】:

      【解决方案2】:

      考虑为您的值类型扩展 GenericWritable。您需要定义允许的类集(在您的情况下为 SQOOP_REC1 和 SQOOP_REC2),并且效率不高,因为它在 readFields 方法中创建了新的对象实例(但如果您有一小部分类,则可以覆盖它,只需拥有两种类型的实例变量,以及一个表示哪一种有效的标志)

      【讨论】:

        【解决方案3】:

        好的,我想我知道该怎么做了。根据 Doug Cutting 本人提出的建议

        http://grokbase.com/t/hadoop/common-user/083gzhd6zd/multiple-output-value-classes

        我使用 ObjectWritable 封装了类

        ObjectWritable obj = new ObjectWritable(SQOOP_REC2.class,sqoop_rec2);
        

        然后在 Reduce 端,我可以获取包装类的名称并将其转换回原始类。

        if(val.getDeclaredClass().getName().equals("SQOOP_REC2")){
                        SQOOP_REC2temp = (SQOOP_REC2) val.get();
        

        别忘了

                job.setMapOutputValueClass(ObjectWritable.class);
        

        【讨论】:

          猜你喜欢
          • 2020-01-23
          • 1970-01-01
          • 2017-06-27
          • 1970-01-01
          • 2021-07-08
          • 1970-01-01
          • 1970-01-01
          • 1970-01-01
          • 2023-03-13
          相关资源
          最近更新 更多