在Hadoop'中使用关系名/表名/文件名;s MapReduce
有没有办法在MapReduce的Map和Reduce中使用关系名称?我正在尝试使用Hadoop的MapReduce进行设置差异 输入:2个包含术语列表的R和S文件。(我将用t表示一个术语) 目标:查找R-S,即R中的术语而非S中的术语 方法: 映射器:根据t来自R还是S,吐出t->R或t->S。因此,映射输出以t作为键,以文件名作为值 减速器:如果t的值列表仅包含R,则输出t->t 我需要用文件名来标记这些术语吗?或者还有别的办法吗 我为Set Union做的一些事情的源代码(在本例中不需要任何文件名)。我只是想用这个例子来说明Mapper中文件名的不可用性在Hadoop'中使用关系名/表名/文件名;s MapReduce,hadoop,mapreduce,Hadoop,Mapreduce,有没有办法在MapReduce的Map和Reduce中使用关系名称?我正在尝试使用Hadoop的MapReduce进行设置差异 输入:2个包含术语列表的R和S文件。(我将用t表示一个术语) 目标:查找R-S,即R中的术语而非S中的术语 方法: 映射器:根据t来自R还是S,吐出t->R或t->S。因此,映射输出以t作为键,以文件名作为值 减速器:如果t的值列表仅包含R,则输出t->t 我需要用文件名来标记这些术语吗?或者还有别的办法吗 我为Set Union做的一些事情的源代码(在本例中不需要任何
public class Union {
public static class Map extends MapReduceBase implements Mapper<LongWritable, Text, Text, Text> {
public void map(LongWritable key, Text value, OutputCollector output, Reporter reporter) throws IOException {
output.collect(value, value);
}
}
public static class Reduce extends MapReduceBase implements Reducer<Text, Text, Text, Text> {
public void reduce(Text key, Iterator<Text> values, OutputCollector<Text, Text> output, Reporter reporter) throws IOException{
while (values.hasNext())
{
output.collect(key, values.next());
break;
}
}
}
public static void main(String[] args) throws Exception {
JobConf conf = new JobConf(Union.class);
conf.setJobName("Union");
conf.setOutputKeyClass(Text.class);
conf.setOutputValueClass(Text.class);
conf.setMapperClass(Map.class);
conf.setCombinerClass(Reduce.class);
conf.setReducerClass(Reduce.class);
conf.set("mapred.job.queue.name", "myQueue");
conf.setNumReduceTasks(5);
conf.setInputFormat(TextInputFormat.class);
conf.setOutputFormat(TextOutputFormat.class);
FileInputFormat.setInputPaths(conf, new Path(args[0]));
FileOutputFormat.setOutputPath(conf, new Path(args[1]));
JobClient.runJob(conf);
}
}
公共类联合{
公共静态类映射扩展MapReduceBase实现映射器{
公共void映射(LongWritable键、文本值、OutputCollector输出、Reporter报告器)引发IOException{
输出。收集(值,值);
}
}
公共静态类Reduce扩展MapReduceBase实现Reducer{
公共void reduce(文本键、迭代器值、OutputCollector输出、Reporter报告器)引发IOException{
while(values.hasNext())
{
collect(key,values.next());
打破
}
}
}
公共静态void main(字符串[]args)引发异常{
JobConf conf=newjobconf(Union.class);
conf.setJobName(“联合”);
conf.setOutputKeyClass(Text.class);
conf.setOutputValueClass(Text.class);
conf.setMapperClass(Map.class);
conf.setCombinerClass(Reduce.class);
conf.setReducerClass(Reduce.class);
conf.set(“mapred.job.queue.name”、“myQueue”);
conf.setNumReduceTasks(5);
conf.setInputFormat(TextInputFormat.class);
conf.setOutputFormat(TextOutputFormat.class);
setInputPath(conf,新路径(args[0]);
setOutputPath(conf,新路径(args[1]);
runJob(conf);
}
}
如您所见,我无法识别哪个键->值对(映射器的输入)来自哪个文件。我是不是忽略了一些简单的事情
非常感谢。我会像你回答的那样实施你的问题。这正是MapReduce的本意。
我猜您的问题实际上是将相同值的n倍写入HDFS?
编辑: 从我的评论粘贴到那里 啊,我明白了;)我对“旧”API不太熟悉,但您可以通过以下方式“查询”您的记者:
reporter.getInputSplit();
这将返回一个名为InputSplit的接口。这很容易转换为“FileSplit”。在FileSplit对象中,您可以使用“split.getPath()”获取路径。从Path对象中,您只需要调用getName()方法。
所以这个片段应该适合您:
FileSplit fsplit = reporter.getInputSplit(); // maybe cast it down to FileSplit if needed..
String yourFileName = fsplit.getPath().getName();
谢谢你,托马斯。我已经更新了我的问题代码片段。我希望这能澄清我的问题。我更关心的是如何在映射器中获取文件名。啊,我得到了;)我不太熟悉“旧”API,但您可以使用:Reporter.getInputSplit()查询您的Reporter。这将返回一个名为InputSplit的接口。这很容易转换为“FileSplit”。在FileSplit对象中,您可以使用“split.getPath()”获取路径。从Path对象,您只需要调用getName()方法。NP:)很高兴我帮助了您;)