Java命令行界面(第1部分):Apache Commons CLI

尽管我通常使用Groovy编写要从命令行运行的JVM托管脚本,但是有时候我需要解析Java应用程序中的命令行参数,并且有很多库可供Java开发人员用来解析命令行参数。 在本文中,我将介绍这些Java命令行解析库中最著名的一种: Apache Commons CLI 。

我以前曾在Apache Commons CLI上发表过博客 ,但该文章已有八年历史,描述了Apache Commons CLI 1.1 。 自那以后,我在那篇文章中演示的两个类GnuParser和PosixParser被弃用了。 本篇文章中的示例基于Apache Commons CLI 1.4,并使用CLI 1.3中引入的更新的DefaultParser来替代GnuParserPosixParser

Apache Commons CLI文档的“ 简介 ”介绍了Commons CLI如何完成“命令行处理的三个阶段”(“定义”,“解析”和“询问”)。 这三个阶段在Commons CLI中映射到Option和Options类(“定义”), CommandLineParser接口(“ parsing”)和CommandLine类(“询问”)。

对于此处使用Apache Commons CLI构建的示例,预期的命令行参数相对简单。 一个参数是可选的,并且在指定时表示启用了详细输出。 另一个参数是必需的,用于指定虚构应用程序要处理的文件。 可选参数没有与该标志关联的值,并表示为-v--verbose 。 必需的参数后应跟一个值,该值是文件的路径和名称。 该标志是-f--file 。 下一个代码清单演示了如何使用Commons CLI的Option.Builder (由Commons CLI 1.3引入)来构建预期的选项,作为“定义”阶段的一部分。

在“定义阶段”使用Apache Commons CLI Option.Builder示例

/*** "Definition" stage of command-line parsing with Apache Commons CLI.* @return Definition of command-line options.*/
private static Options generateOptions()
{final Option verboseOption = Option.builder("v").required(false).hasArg(false).longOpt(VERBOSE_OPTION).desc("Print status with verbosity.").build();final Option fileOption = Option.builder("f").required().longOpt(FILE_OPTION).hasArg().desc("File to be processed.").build();final Options options = new Options();options.addOption(verboseOption);options.addOption(fileOption);return options;
}

如上例所示,为Apache Commons CLI实现的“ 构建器 ”模式具有构建器模式的优点,例如在一条语句中以完全完成的状态创建Option ,并使用高度可读的构建器方法来设置该实例的各个字段。 我在Apache Commons CLI上的较旧文章演示了如何使用替代的传统构造方法实例化Option实例。

定义了命令行选项之后,该进入“解析”阶段了,下一个代码清单演示了如何通过简单地调用方法CommandLinePaser.parse()来使用Apache Commons CLI进行解析。

使用Commons CLI解析命令行选项

/*** "Parsing" stage of command-line processing demonstrated with* Apache Commons CLI.** @param options Options from "definition" stage.* @param commandLineArguments Command-line arguments provided to application.* @return Instance of CommandLine as parsed from the provided Options and*    command line arguments; may be {@code null} if there is an exception*    encountered while attempting to parse the command line options.*/
private static CommandLine generateCommandLine(final Options options, final String[] commandLineArguments)
{final CommandLineParser cmdLineParser = new DefaultParser();CommandLine commandLine = null;try{commandLine = cmdLineParser.parse(options, commandLineArguments);}catch (ParseException parseException){out.println("ERROR: Unable to parse command-line arguments "+ Arrays.toString(commandLineArguments) + " due to: "+ parseException);}return commandLine;
}

请注意,此代码使用更新版本的Apache Commons CLI实例化DefaultParser进行解析,而不是像旧代码中那样实例化PosxParserGnuParser

定义了命令行对象并解析了命令行之后,就该开始进行查询了。 下一个代码清单展示了Apache Commons CLI对命令行询问的支持。

使用Commons CLI询问命令行

final boolean verbose =commandLine.hasOption(VERBOSE_OPTION);
final String fileName =commandLine.getOptionValue(FILE_OPTION);
out.println("The file '" + fileName + "' was provided and verbosity is set to '" + verbose + "'.");

上面的代码清单演示了如何使用CommandLine.hasOption()来确定是否存在选项的特定标志,而无需考虑是否为该标志提供了值(在我们的示例中, -v / --verbose是适当的)。 同样,代码显示CommandLine.getOptionValue()可用于获取与所提供的命令行标志关联的值(在我们的示例中, -f / --file选项合适)。

下一个屏幕快照演示了简单示例的输出,该示例的代码清单如上所示,它们演示了对上述详细程度和文件路径/位置命令行选项的支持。

当命令行参数不包含必需的命令行参数时,第二个屏幕快照演示了Commons CLI的输出。

对于任何用于构建Java命令行解析的框架,有用的功能是支持使用和帮助信息的能力。 这是通过Commons CLI的HelpFormatter完成的。 下一个代码清单演示了如何使用HelpFormatter来打印帮助和用法信息,并且代码清单后的屏幕快照演示了使用时的帮助和用法外观。

通过Commons CLI获取“用法”和“帮助”详细信息

/*** Generate usage information with Apache Commons CLI.** @param options Instance of Options to be used to prepare*    usage formatter.* @return HelpFormatter instance that can be used to print*    usage information.*/
private static void printUsage(final Options options)
{final HelpFormatter formatter = new HelpFormatter();final String syntax = "Main";out.println("\n=====");out.println("USAGE");out.println("=====");final PrintWriter pw  = new PrintWriter(out);formatter.printUsage(pw, 80, syntax, options);pw.flush();
}/*** Generate help information with Apache Commons CLI.** @param options Instance of Options to be used to prepare*    help formatter.* @return HelpFormatter instance that can be used to print*    help information.*/
private static void printHelp(final Options options)
{final HelpFormatter formatter = new HelpFormatter();final String syntax = "Main";final String usageHeader = "Example of Using Apache Commons CLI";final String usageFooter = "See http://marxsoftware.blogspot.com/ for further details.";out.println("\n====");out.println("HELP");out.println("====");formatter.printHelp(syntax, usageHeader, options, usageFooter);
}

这篇文章演示了如何使用Apache Commons CLI实现与Java应用程序中的命令行解析有关的一些最常见功能,包括选项“定义”,命令行参数“解析”,解析后的命令行参数“查询”,以及与命令行参数相关的帮助/使用详细信息。 在选择框架或库来帮助使用Java进行命令行解析时,需要考虑以下Apache Commons CLI的其他特征。

  • Apache Commons CLI是开源的,并获得了Apache License 2.0版的许可 。
  • 当前版本的Apache Commons CLI( 1.4 )需要J2SE 5或更高版本。
  • Apache Commons CLI不需要单独下载或引用任何第三方库 。
  • Apache Commons CLI 1.4主JAR( commons-cli-1.4.jar )的大小约为53 MB。
  • Apache Groovy通过CliBuilder基于Apache Commons CLI提供了现成的命令行解析功能。
  • Maven资源库显示了对Apache Commons CLI(包括Apache Groovy)的 近1800种依赖 。
  • Apache Commons CLI已经存在了一段时间。 它最初的1.0版本是在2002年11月。

对我来说,在简单Java应用程序中实现命令行界面时,Apache Commons CLI的最大优势之一就是我已经熟悉Groovy内置的CliBuilder用法 。 因为与基于Java的脚本相比,我更经常将Groovy用于基于命令行的简单脚本和工具,所以对Groovy熟悉基本的Apache Commons CLI用法对返回Java很有帮助。

其他参考

  • Apache Commons CLI
  • Apache Commons CLI简介
  • Apache Commons CLI使用场景
  • Apache Commons CLI API文档
  • 使用Apache Commons CLI进行命令行解析 (我2008年在Apache Commons CLI上的帖子)

翻译自: https://www.javacodegeeks.com/2017/06/java-command-line-interfaces-part-1-apache-commons-cli.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/349221.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

python自带的idle输入python_打开python自带IDLE出的问题

打开python自带IDLE编辑器时出的问题IDLE cant bind to a TCP/IP port, which is necessary tocommunicate with its Python execution server. This might bebecause no networking is installed on this computer. Run IDLEwith the -n command line switch to start without…

linux 虚拟机新增磁盘,linux(虚拟机)下新增磁盘配置

Linux的硬盘识别:(1)”fdisk -l”命令可以列出系统中当前连接的硬盘设备和分区信息.新硬盘没有分区信息,则只显示硬盘大小信息.(2)创建新硬盘分区命令参数:fdisk可以用m命令来看fdisk命令的内部命令;a:命令指定启动分区;d&#xf…

丙烯怎么做成流体丙烯_韧性好强度高的聚丙烯复合材料怎么做?让人工智能来帮忙...

01背景介绍聚丙烯(PP)是一种应用广泛的通用塑料,价格便宜、力学性能好、热稳定性高,在机械、汽车、电子电器、建筑、纺织、包装和食品工业等领域应用广泛。聚丙烯韧性和冲击强度不高,限制了它的应用。加入热塑性弹性体(TPE),如苯乙…

1.x到2.x的迁移:可观察与可观察:RxJava FAQ

标题不是错误。 rx.Observable 1.x的io.reactivex.Observable与2.x的io.reactivex.Observable完全不同。 盲目升级rx依赖关系并重命名项目中的所有导入将进行编译(稍作更改),但不能保证相同的行为。 在项目的早期, Observable in …

linux 线程 拷贝,linux下实现多线程拷贝命令

实现多线程拷贝命令,如:./multithread_copy srcfile destfile N(拷贝线程个数)难点:内存映射mmap。给每一个线程合理的分配任务。多线程的实现。具体的实现代码如下:/********************************************************************…

vivado安装_Vivado下载与安装指南

Vivado下载与安装指南目前,vivado已推出2019.1版本,实验室所安装的为2018.3版本,由于软件向下兼容的特性,建议安装2018版本,若安装2019版本,请自带笔记本,安装过程与之前没有差别,这…

linux中kafka主题修改分区,kafka_2.11-2.0.0的部署与配置修改

1 [yunmini01 config]$ pwd2 /app/kafka/config3 [yunmini01 config]$ vim server.properties4 ############################# Server Basics #############################5 # 每一个broker在集群中的唯一标示★★★6 # 比如mini01 为0 mini02 为1 mini03 为27 broker.id089…

python中字符串乘法_python leetcode 字符串相乘实例详解

给定两个以字符串形式表示的非负整数 num1 和 num2 ,返回 num1 和 num2 的乘积,它们的乘积也表示为字符串形式。示例 1:输入: num1 "2", num2 "3"输出: "6"示例 2:输入: num1 "123", num2 "456&quo…

嵌入式基于linux电机控制器,基于嵌入式Linux的移动机器人控制系统

使用select机制监控是否语音识别结果,在超出等待时间后,会退出等待并重新初始化语音模块LD3320,释放公共资源,这样也使得系统能够及时响应LD3320的MP3播放功能,避免了在长时间没有语音识别结果时,系统进入卡…

jdk8运行jdk7的代码_即使在jdk中也有错误的代码

jdk8运行jdk7的代码Java 7,TreeSet和NullPointerException。 最近,我尝试用Java 7编译一个用Java 6开发的项目。在执行测试过程中发生了很多有趣的事情,在Java 6中使用Java 7平稳运行的测试失败了! 因此,我必须理解为什…

zen of python什么意思_如何理解「The Zen of Python」?

import thisThe Zen of Python, by Tim PetersPython之禅 ,by Tim PetersBeautiful is better than ugly.优美好于丑陋(Python 以优美的代码为其风格,不要写丑陋的代码)Explicit is better than implicit.明了好于隐晦(Python的每一行代码、每一个变量、…

linux用pipe创建的文件类型,linux文件类型之 管道

inux管道管道是Linux中很重要的一种通信方式,是把一个程序的输出直接连接到另一个程序的输入,常说的管道多是指无名管道,无名管道只能用于具有亲缘关系的进程之间,这是它与有名管道的最大区别。有名管道叫namedpipe或者FIFO(先进先出),可以用函数mkfifo(…

Spring Webflux – Kotlin DSL –实现的演练

在先前的博客文章中,我描述了Spring Web Framework中的响应式编程支持Spring Webflux如何使用基于Kotlin的DSL使用户能够以非常直观的方式描述路由。 在这里,我想探索一些底层实现。 描述一组端点的样本DSL看起来像这样: package sample.ro…

python 正则表达式提取数据_Python爬虫教程-19-数据提取-正则表达式(re)

本篇主页内容:match的基本使用,search的基本使用,findall,finditer的基本使用,匹配中文,贪婪与非贪婪模式Python爬虫教程-19-数据提取-正则表达式(re)正则表达式:一套规则,可以在字符串文本中进…

c语言作业请输入一个运算符,C语言书面作业1(有答案版)..doc

C语言书面作业1(有答案版).书面作业1(数据类型、变量、输入/输出、运算符与表达式、选择结构、循环结构)一、判断题:在正确的说法前面填写T,在错误的说法前面填写F(每题1分)[得分: ]()()()()标识符中可以出现下划线但它不可以放在标识符的开头…

windows server 驱动精灵_还在用Windows文件共享?我来教你一键摆脱Windows海量小文件使用和备份的噩梦...

每当我问到客户,“你用什么存储产品作为文件共享?”经常听到的一个答案(自豪滴)是,“文件共享需要存储么?我们用Windows就可以做到。”Windows就是个百宝箱,什么都能往里装,就像你家冰箱一样。众所周知&…

c语言编写日历作业,c语言实现一个简单日历

满足三个需求:1.输入一个年份,输出是在屏幕上显示该年的日历。假定输入的年份在1940-2040年之间。2.输入年月,输出该月的日历。3.输入年月日,输出距今天还有多少天,星期几,是否是公历…

将EntityManager.refresh添加到所有Spring数据存储库

在我以前的文章《从Spring Data JPA访问EntityManager》中,我展示了如何扩展单个Spring Data JPA存储库以访问EntityManager.refresh方法。 这篇文章演示了如何将EntityManager.refresh添加到所有Spring Data Repository。 源代码 第一步是定义您的界面- package …

pb 应用 迁移 linux_功能化生物炭应用研究取得系列进展

土壤营养元素流失、重金属污染是当前全球面临的突出环境问题。生物炭因其具有比表面积较大、吸附性能高和成本低等优点而在环境修复领域日益受到广泛关注,被作为水处理吸附剂、土壤修复改良剂广泛应用于农业土壤改良和环境中重金属的修复和钝化。但通常情况下&#…

Java命令行界面(第26部分):CmdOption

由于Tweet,我了解了本系列中第26个基于Java的功能强大的库,该库用于解析命令行参数 。 CmdOption在其GitHub主页上被描述为“一个通过注释配置的,用于Java 5应用程序的简单注释驱动的命令行解析器工具包。” 该项目的副标题是“命令行解析从未…