Java中命令行参数解析
2016-06-19 本文已影响4808人
yang2yang
Apache.Commons.CLI
The Apache Commons CLI library provides an API for parsing command line options passed to programs. It's also able to print help messages detailing the options available for a command line tool.
Commons CLI supports different types of options:
- POSIX like options (ie.
tar -zxvf foo.tar.gz
) - GNU like long options (ie.
du --human-readable --max-depth=1
) - Java like properties (ie.
java -Djava.awt.headless=true -Djava.net.useSystemProxies=true Foo
) - Short options with value attached (ie.
gcc -O2 foo.c
) - long options with single hyphen (ie.
ant -projecthelp
)
Maven仓库
<dependency>
<groupId>commons-cli</groupId>
<artifactId>commons-cli</artifactId>
<version>1.3</version>
</dependency>
Example:
如果想要得到下面的一个参数列表:
java wordcount [-help] [-O][value] [-c] <filename> otherfilename
//演示使用的是1.3的版本
public static void main(String[] args) throws IOException, ParseException {
//option的容器
Options options = new Options();
//boolean型的option
options.addOption("help",false,"help information");
//当第二参数是true时,可以是这样的参数 -O4
options.addOption("O",true,"you can set a value after the O");
Option c = Option.builder("c") //option的名字,判断的时候要使用这个名字
.required(false) //是否必须有这个选项
.hasArg() //带一个参数
.argName("filename") //参数的名字
.desc("return sum of characters") //描述
.build(); //必须有
//将c这个option添加进去
options.addOption(c);
//parser
CommandLineParser parser = new DefaultParser();
CommandLine cmd = parser.parse(options,args);
//询问是否有help
if(cmd.hasOption("help")) {
//调用默认的help函数打印
HelpFormatter formatter = new HelpFormatter();
formatter.printHelp( "java wordcount [OPTION] <FILENAME>", options );
return;
}
if(cmd.hasOption("c")){
// 获得相应的选项(c)的参数
String filename = cmd.getOptionValue("c");
System.out.println(filename);
// do something
}
//将除了选项之外的参数打印出来 otherfilename
String[] s = cmd.getArgs();
for(String e : s){
System.out.println("="+e);
}
PS:自己的CommandLine Parser即是Scanner
疑惑
Option c = Option.builder("c") //option的名字 貌似没什么卵用?
.required(false) //是否必须有这个选项
.hasArg() //带一个参数
.argName("filename") //参数的名字
.desc("return sum of characters") //描述
.build(); //必须有
为什么创建Option的时候要用一个build这样一个中间的类来创建,不直接使用new之类的关键字创建不是更好吗?反正我看了一下build()
函数也只是将属性直接赋值过去而已?是用了什么设计模式吗?还是为了安全考虑?
其实最后还是内部给new出来了不是吗?
public Option build()
{
if (opt == null && longOpt == null)
{
throw new IllegalArgumentException("Either opt or longOpt must be specified");
}
return new Option(this);
}
然后就是直接复制过去,其实完全可以将Builder中的一些函数给Option中,不是吗?
private Option(final Builder builder)
{
this.argName = builder.argName;
this.description = builder.description;
this.longOpt = builder.longOpt;
this.numberOfArgs = builder.numberOfArgs;
this.opt = builder.opt;
this.optionalArg = builder.optionalArg;
this.required = builder.required;
this.type = builder.type;
this.valuesep = builder.valuesep;
}