java - 如何使用 picocli 处理多种类型的选项
问题描述
我正在将现有应用程序转换为使用 picocli。现有选项之一如下所示:
-t, --threads [1, n] for fixed thread pool, 'cpus' for number of cpus, 'cached' for cached
这允许选项是一个正整数或几个特殊字符串之一。现有代码将其视为字符串,如果它不是特殊字符串之一,则将其传递给Integer.parseInt
.
当然,我可以用 picocli 做同样的事情,但我想知道是否有更好的方法来处理这个问题。例如,允许多个字段用于同一个选项,并根据传递的内容填写适当的字段?这也可能允许我对可能的字符串选项使用枚举。
解决方案
一个想法是为此创建一个类,例如,maybe ThreadPoolSize
,它封装固定数值或动态值的枚举。您需要为此数据类型创建一个自定义转换器。
然后您可以按如下方式定义选项:
@Option(names = { "-t", "--threads" }, converter = ThreadPoolSizeConverter.class,
description = "[1, n] for fixed thread pool, 'cpus' for number of cpus, 'cached' for cached")
ThreadPoolSize threadPoolSize;
线程池大小和转换器的自定义数据类型可能如下所示:
class ThreadPoolSize {
enum Dynamic { cpus, cached }
int fixed = -1; // if -1, then use the dynamic value
Dynamic dynamic; // if null, then use the fixed value
}
class ThreadPoolSizeConverter implements CommandLine.ITypeConverter<ThreadPoolSize> {
@Override
public ThreadPoolSize convert(String value) throws Exception {
ThreadPoolSize result = new ThreadPoolSize();
try {
result.fixed = Integer.parseInt(value);
if (result.fixed < 1) {
throw new CommandLine.TypeConversionException("Invalid value " +
value + ": must be 1 or more.");
}
} catch (NumberFormatException nan) {
try {
result.dynamic = ThreadPoolSize.Dynamic.valueOf(
value.toLowerCase(Locale.ENGLISH));
} catch (IllegalArgumentException ex) {
throw new CommandLine.TypeConversionException("Invalid value " +
value + ": must be one of " +
Arrays.toString(ThreadPoolSize.Dynamic.values()));
}
}
return result;
}
}
推荐阅读
- php - PHP DOMDocument 无法创建-tag
- java - Can't succeed in using multiple textures in a fragment
- android - [Unity][Firebase] Dex:将字节码转换为 dex 时出错:构建播放器时出错
- c# - 无法从其他表格中找到表 0
- python - 双链表中间插入不起作用
- c - GTK3.0中如何使用gstreamer同时播放视频和音频
- django - 阻止 Django 在 admin 中自动填充多字段
- android - Android Studio 在 hello world 示例中使用 firebase 数据库崩溃
- java - 替换 switch 语句 Java
- python - Selenium Python 帮助获取表单元素