Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/330.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 将不同的参数传递给每个映射器_Java_Hadoop - Fatal编程技术网

Java 将不同的参数传递给每个映射器

Java 将不同的参数传递给每个映射器,java,hadoop,Java,Hadoop,我有一个工作,使用多个映射器和一个减速机。映射器几乎相同,只是它们用于生成结果的字符串的值不同 目前我有几个类,我提到的字符串的每个值对应一个-感觉应该有更好的方法,不需要太多代码重复。是否有方法将这些字符串值作为参数传递给映射器 我的工作是这样的: Input File A ----> Mapper A using String "Foo" ----+ |

我有一个工作,使用多个映射器和一个减速机。映射器几乎相同,只是它们用于生成结果的
字符串的值不同

目前我有几个类,我提到的
字符串的每个值对应一个-感觉应该有更好的方法,不需要太多代码重复。是否有方法将这些
字符串
值作为参数传递给映射器

我的工作是这样的:

Input File A  ---->  Mapper A using
                       String "Foo"  ----+
                                         |--->  Reducer
                     Mapper B using  ----+
Input File B  ---->    String "Bar" 
Input File A  ---->  GenericMapper parameterized
                               with String "Foo" ----+
                                                     |--->  Reducer
                     GenericMapper parameterized ----+ 
Input File B  ---->            with String "Bar"
if (context.getInputSplit() instanceof FileSplit) {
    FileSplit fileSplit = (FileSplit) context.getInputSplit();
    Path inputPath = fileSplit.getPath();
    String fileId = ... //parse inputPath into a file id
    ...
}
我想把它变成这样:

Input File A  ---->  Mapper A using
                       String "Foo"  ----+
                                         |--->  Reducer
                     Mapper B using  ----+
Input File B  ---->    String "Bar" 
Input File A  ---->  GenericMapper parameterized
                               with String "Foo" ----+
                                                     |--->  Reducer
                     GenericMapper parameterized ----+ 
Input File B  ---->            with String "Bar"
if (context.getInputSplit() instanceof FileSplit) {
    FileSplit fileSplit = (FileSplit) context.getInputSplit();
    Path inputPath = fileSplit.getPath();
    String fileId = ... //parse inputPath into a file id
    ...
}
编辑:这里是我目前拥有的两个简化映射器类。它们准确地代表了我的实际情况

class MapperA extends Mapper<Text, Text, Text, Text> {
    public void map(Text key, Text value, Context context) {
        context.write(key, new Text(value.toString() + "Foo"));
    }
}

class MapperB extends Mapper<Text, Text, Text, Text> {
    public void map(Text key, Text value, Context context) {
        context.write(key, new Text(value.toString() + "Bar"));
    }
}
类MapperA扩展了Mapper{
公共无效映射(文本键、文本值、上下文){
write(键,新文本(value.toString()+“Foo”);
}
}
类MapperB扩展了Mapper{
公共无效映射(文本键、文本值、上下文){
write(键,新文本(value.toString()+“Bar”);
}
}

编辑:每个映射程序应该使用的字符串仅取决于数据来自哪个文件。除了通过文件名,无法区分文件。

也许您可以在映射器中使用if语句在字符串之间进行选择。什么取决于一个字符串或另一个字符串的使用


或者可能使用抽象映射器类。

可能是这样的

abstract class AbstractMapper extends Mapper<Text, Text, Text, Text> {
    protected String text;
    public void map(Text key, Text value, Context context) {
        context.write(key, new Text(value.toString() + text));
    }
}
class MapperImpl1 extends AbstractMapper{
    @Override
    public void map(Text key, Text value, Context context) {
        text = "foo";
        super.map();
    }
}
class MapperImpl2 extends AbstractMapper{
        @Override
        public void map(Text key, Text value, Context context) {
            text = "bar";
            super.map();
        }
    }
抽象类AbstractMapper扩展了Mapper{
受保护的字符串文本;
公共无效映射(文本键、文本值、上下文){
write(键,新文本(value.toString()+文本));
}
}
类MapperImpl1扩展了AbstractMapper{
@凌驾
公共无效映射(文本键、文本值、上下文){
text=“foo”;
super.map();
}
}
类MapperImpl2扩展了AbstractMapper{
@凌驾
公共无效映射(文本键、文本值、上下文){
text=“bar”;
super.map();
}
}

假设您使用文件输入格式,您可以在映射器中获得当前输入文件名,如下所示:

Input File A  ---->  Mapper A using
                       String "Foo"  ----+
                                         |--->  Reducer
                     Mapper B using  ----+
Input File B  ---->    String "Bar" 
Input File A  ---->  GenericMapper parameterized
                               with String "Foo" ----+
                                                     |--->  Reducer
                     GenericMapper parameterized ----+ 
Input File B  ---->            with String "Bar"
if (context.getInputSplit() instanceof FileSplit) {
    FileSplit fileSplit = (FileSplit) context.getInputSplit();
    Path inputPath = fileSplit.getPath();
    String fileId = ... //parse inputPath into a file id
    ...
}
您可以根据需要解析inputPath,例如仅使用文件名或仅使用分区id等,以生成标识输入文件的唯一id。 例如:

/some/path/A -> A
/some/path/B -> B
为驱动程序中每个可能的文件“id”配置属性:

conf.set("my.property.A", "foo");
conf.set("my.property.B", "bar"); 
在映射器计算文件“id”中,如上所述,并获取值:

conf.get("my.property." + fileId);

我认为一些实际的映射程序代码会很棒。或者至少是您当前的映射器structure@maffelbaffel我添加了一些代码。除了附加的字符串之外,映射器A和B有什么不同?您是否使用多个输入?你有多少文件?从驱动程序代码中,您可以传递与每个文件名关联的“字符串”,从map()中,您可以获取当前正在处理的文件名并附加必要的密钥。我相信我还没有完全理解这个问题。我是否遗漏了什么。如果我没有弄错的话,这种方法将无助于将代码简化为唯一的映射器clas,因为它仍然需要为每种映射器类型定制实现。我相信这与我的评论相同:)