Hadoop中通过ToolRunner和Configured实现直接读取命令行动态出入reduce task数量,jar文件等...
一個典型的實現Tool的程序:
| /** MyApp 需要從命令行讀取參數,用戶輸入命令如, $bin/hadoop jar MyApp.jar -archives test.tgz ?arg1 arg2 -archives 為hadoop通用參數,arg1 ,arg2為job的參數 */ public class MyApp extends Configured implements Tool { ???????? //implemet Tool’s run ???????? public int run(String[] args) throws Exception { ?????????????????? Configuration conf = getConf(); ?????????????????? // Create a JobConf using the processed conf ?????????????????? JobConf job = new JobConf(conf, MyApp.class); ?????????????????? // Process custom command-line options ?????????????????? Path in = new Path(args[1]); ?????????????????? Path out = new Path(args[2]); ?????????????????? // Specify various job-specific parameters ?????????????????? job.setJobName(“my-app”); ?????????????????? job.setInputPath(in); ?????????????????? job.setOutputPath(out); ?????????????????? job.setMapperClass(MyApp.MyMapper.class); ?????????????????? job.setReducerClass(MyApp.MyReducer.class); ?????????????????? ? ?????????????????? JobClient.runJob(job); ???????? } ??????? ???????? public static void main(String[] args) throws Exception { ?????????????????? // args由ToolRunner來處理 ?????????????????? int res = ToolRunner.run(new Configuration(), new MyApp(), args); ?????????????????? System.exit(res); ???????? } } |
?
說明:
使用ToolRunner讓參數傳遞更簡單,關于MapReduce運行和參數配置,你是否有下面的煩惱:
A: 將MapReduce Job配置參數寫到java代碼里,一旦變更意味著修改java文件源碼、編譯、打包、部署一連串事情。
B:當MapReduce 依賴配置文件的時候,你需要手工編寫java代碼使用DistributedCache將其上傳到HDFS中,以便map和reduce函數可以讀取。
C:當你的map或reduce 函數依賴第三方jar文件時,你在命令行中使用”-libjars”參數指定依賴jar包時,但根本沒生效。
D:其實,Hadoop有個ToolRunner類,它是個好東西,簡單好用。無論在《Hadoop權威指南》還是Hadoop項目源碼自帶的example,都推薦使用ToolRunner。
?
下面我們看下src/example目錄下WordCount.Java文件,它的代碼結構是這樣的:
public class WordCount {
???// 略...
???public static void main(String[] args) throws Exception {
???????Configuration conf = new Configuration();
???????String[] otherArgs = new GenericOptionsParser(conf,
???????????????????????????????????????????args).getRemainingArgs();
???????// 略...
???????Job job = new Job(conf, "word count");
???????// 略...
???????System.exit(job.waitForCompletion(true) ? 0 : 1);
??? }
}
WordCount.java中使用到了GenericOptionsParser這個類,它的作用是將命令行中參數自動設置到變量conf中。舉個例子,比如我希望通過命令行設置reduce task數量,就這么寫:bin/hadoop jar MyJob.jar com.xxx.MyJobDriver -Dmapred.reduce.tasks=5
上面這樣就可以了,不需要將其硬編碼到java代碼中,很輕松就可以將參數與代碼分離開。
其它常用的參數還有”-libjars”和-“files”,使用方法一起送上:
bin/hadoop jar MyJob.jar com.xxx.MyJobDriver -Dmapred.reduce.tasks=5\
???-files ./dict.conf? \
???-libjars lib/commons-beanutils-1.8.3.jar,lib/commons-digester-2.1.jar
參數”-libjars”的作用是上傳本地jar包到HDFS中MapReduce臨時目錄并將其設置到map和reduce task的classpath中;參數”-files”的作用是上傳指定文件到HDFS中mapreduce臨時目錄,并允許map和reduce task讀取到它。這兩個配置參數其實都是通過DistributeCache來實現的。
至此,我們還沒有說到ToolRunner,上面的代碼我們使用了GenericOptionsParser幫我們解析命令行參數,編寫ToolRunner的程序員更懶,它將GenericOptionsParser調用隱藏到自身run方法,被自動執行了,修改后的代碼變成了這樣:
?
public class WordCount extends Configuredimplements Tool {
?
???@Override
???public int run(String[] arg0) throws Exception {
???????Job job = new Job(getConf(), "word count");
???????// 略...
???????System.exit(job.waitForCompletion(true) ? 0 : 1);
???????return 0;
??? }
?
???public static void main(String[] args) throws Exception {
???????int res = ToolRunner.run(new Configuration(), new WordCount(), args);
???????System.exit(res);
??? }
}
看看代碼上有什么不同:
讓WordCount繼承Configured并實現Tool接口。
重寫Tool接口的run方法,run方法不是static類型,這很好。
在WordCount中我們將通過getConf()獲取Configuration對象。
?
最終我們得出的總結是:
1、通過使用ToolRunner.run(...)方法,可以更便利的使用hadoop命令行參數。
2、ToolRunner.run(...)通過調用Tool類中的run(String[])方法來運行hadoop程序,并默認加載core-default.xml與core-site.xml中的參數。
?
在程序運行時,可以通過命令行修改參數,可修改的內容如下:
?
?
?
總結
以上是生活随笔為你收集整理的Hadoop中通过ToolRunner和Configured实现直接读取命令行动态出入reduce task数量,jar文件等...的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Python 调用C函数
- 下一篇: 指针数组的初始化和遍历,并且通过for循