运行Hadoop Jar包报错:参数数量不正确,求排查方案
解决Hadoop WordCount任务参数校验错误
我是Hadoop新手,在Ubuntu系统中参照网上的WordCount MapReduce示例操作,已完成除任务运行外的所有步骤:将输入文件上传至集群,路径为/user/inputdata/test.txt,指定/user/output作为输出目录。执行以下命令:
hadoop jar /home/wasim/Downloads/jar_files/MapReduceDemo.jar MapReduceDemo.WordCounter /user/inputdata/test.txt /user/output
时,收到错误提示:
usage: WordCount <input_file> <output_directory>
我知晓该错误源于Java代码的参数校验,但多次调整命令仍未解决问题,附上相关代码:
package MapReduceDemo; import java.io.IOException; import java.util.Iterator; import java.util.StringTokenizer; import org.apache.hadoop.conf.Configuration; import org.apache.hadoop.fs.Path; import org.apache.hadoop.io.IntWritable; import org.apache.hadoop.io.Text; import org.apache.hadoop.mapreduce.Job; import org.apache.hadoop.mapreduce.Mapper; import org.apache.hadoop.mapreduce.Reducer; import org.apache.hadoop.mapreduce.lib.input.FileInputFormat; import org.apache.hadoop.mapreduce.lib.output.FileOutputFormat; import org.apache.hadoop.util.GenericOptionsParser; public class WordCounter { public static class TokenizeMapper extends Mapper<Object,Text,Text,IntWritable>{ public void map(Object key, Text value, Context context) throws IOException, InterruptedException { StringTokenizer st = new StringTokenizer(value.toString()); Text wordOut = new Text(); IntWritable one = new IntWritable(1); while(st.hasMoreTokens()){ wordOut.set(st.nextToken()); context.write(wordOut, one); } } } public static class SumReducer extends Reducer<Text,IntWritable,Text,IntWritable>{ public void reduce(Text term,Iterable<IntWritable> ones, Context context) throws IOException, InterruptedException { int count = 0; Iterator<IntWritable> iterator = ones.iterator(); while(iterator.hasNext()) { count++; iterator.next(); } IntWritable output = new IntWritable(count); context.write(term, output); } } public static void main(String[] args) throws IOException, ClassNotFoundException, InterruptedException { Configuration conf = new Configuration(); String[] otherArgs = new GenericOptionsParser(conf, args).getRemainingArgs(); if(otherArgs.length !=2) { System.err.println("usage: WordCount <input_file> <output_directory>"); System.exit(2); } Job job = Job.getInstance(conf,"Word Count"); job.setJarByClass(WordCounter.class); job.setMapperClass(TokenizeMapper.class); job.setReducerClass(SumReducer.class); job.setNumReduceTasks(10); job.setOutputKeyClass(Text.class); job.setOutputValueClass(IntWritable.class); FileInputFormat.addInputPath(job,new Path(otherArgs[0])); FileOutputFormat.setOutputPath(job,new Path(otherArgs[1])); boolean status = job.waitForCompletion(true); if(status) { System.exit(0); } else { System.exit(1); } } }
排查与解决步骤
- 清理已存在的输出目录
Hadoop不允许输出目录提前存在,先执行命令删除:
hdfs dfs -rm -r /user/output
- 修正参数校验提示
代码中错误提示写的是WordCount,但主类实际是WordCounter,修改主方法中的提示语句,避免混淆:
if(otherArgs.length !=2) { System.err.println("usage: WordCounter <input_file> <output_directory>"); System.exit(2); }
- 替换参数解析逻辑
GenericOptionsParser可能会处理Hadoop通用参数导致解析异常,若命令中未使用-conf等通用参数,直接用args数组替代原解析逻辑:
// 删除GenericOptionsParser相关代码,替换为: if(args.length !=2) { System.err.println("usage: WordCounter <input_file> <output_directory>"); System.exit(2); } // 后续路径引用改为args FileInputFormat.addInputPath(job,new Path(args[0])); FileOutputFormat.setOutputPath(job,new Path(args[1]));
- 验证jar包结构
检查jar包中是否包含正确的类文件:
jar tf /home/wasim/Downloads/jar_files/MapReduceDemo.jar | grep WordCounter
确保输出中存在MapReduceDemo/WordCounter.class。
- 重新打包运行
修正代码后重新打包,再执行原命令即可。
内容的提问来源于stack exchange,提问作者Wasim_Khan
相关产品推荐
相关产品推荐

