shu*_*fan 147 command-line rust
该锈教程并没有解释如何在命令行中带参数.fn main()在所有示例中仅显示空参数列表.
从哪个访问命令行参数的正确方法是main什么?
bar*_*jak 162
您可以使用std::env::args或std::env::args_os函数访问命令行参数.两个函数都在参数上返回迭代器.前者迭代Strings(易于使用)但如果其中一个参数不是有效的unicode则会发生混乱.后者迭代OsStrings,从不恐慌.
请注意,迭代器的第一个元素是程序本身的名称(这是所有主要操作系统中的约定),因此第一个参数实际上是第二个迭代元素.
处理结果的简单方法args是将其转换为Vec:
use std::env;
fn main() {
let args: Vec<_> = env::args().collect();
if args.len() > 1 {
println!("The first argument is {}", args[1]);
}
}
Run Code Online (Sandbox Code Playgroud)
您可以使用整个标准迭代器工具箱来处理这些参数.例如,要仅检索第一个参数:
use std::env;
fn main() {
if let Some(arg1) = env::args().nth(1) {
println!("The first argument is {}", arg1);
}
}
Run Code Online (Sandbox Code Playgroud)
Bur*_*hi5 22
Docopt也可用于Rust,它会根据用法字符串为您生成解析器.作为Rust的一个奖励,可以使用宏来自动生成结构并进行基于类型的解码:
docopt!(Args, "
Usage: cp [-a] SOURCE DEST
cp [-a] SOURCE... DIR
Options:
-a, --archive Copy everything.
")
Run Code Online (Sandbox Code Playgroud)
你可以得到args:
let args: Args = Args::docopt().decode().unwrap_or_else(|e| e.exit());
Run Code Online (Sandbox Code Playgroud)
README和文档有很多完整的工作示例.
免责声明:我是该图书馆的作者之一.
对我来说,傻瓜总是觉得太低级,而docopt.rs太神奇了.我想要一些明确而直截了当的东西,如果我需要它还能提供所有功能.
这就是clap-rs派上用场的地方.
感觉有点像Python的argparse.以下是它的外观示例:
let matches = App::new("myapp")
.version("1.0")
.author("Kevin K. <kbknapp@gmail.com>")
.about("Does awesome things")
.arg(Arg::with_name("CONFIG")
.short("c")
.long("config")
.help("Sets a custom config file")
.takes_value(true))
.arg(Arg::with_name("INPUT")
.help("Sets the input file to use")
.required(true)
.index(1))
.arg(Arg::with_name("debug")
.short("d")
.multiple(true)
.help("Sets the level of debugging information"))
.get_matches();
Run Code Online (Sandbox Code Playgroud)
您可以像这样访问您的参数:
println!("Using input file: {}", matches.value_of("INPUT").unwrap());
// Gets a value for config if supplied by user, or defaults to "default.conf"
let config = matches.value_of("CONFIG").unwrap_or("default.conf");
println!("Value for config: {}", config);
Run Code Online (Sandbox Code Playgroud)
(从官方文件复制)
如果没有必要,我个人不喜欢在较小的项目中使用库,并且在 Rust 中解析命令行参数非常简单:
fn main() {
let config: String;
let mut args = env::args().skip(1);
while let Some(arg) = args.next() {
match &arg[..] {
"-h" | "--help" => help(),
"--version" => {
println!("{} {}", prog().unwrap_or_default(), VERSION);
}
"-q" | "--quiet" => {
println!("Quiet mode is not supported yet.");
}
"-v" | "--verbose" => {
println!("Verbose mode is not supported yet.");
}
"-c" | "--config" => {
if let Some(arg_config) = args.next() {
config = arg_config;
} else {
panic!("No value specified for parameter --config.");
}
}
_ => {
if arg.starts_with('-') {
println!("Unkown argument {}", arg);
} else {
println!("Unkown positional argument {}", arg);
}
}
}
}
}
Run Code Online (Sandbox Code Playgroud)
为了处理非字符串参数,您可以使用 String::parse() 方法尝试将给定字符串解析为指定类型:
"-s" | "--size" => {
if let Some(arg_size) = arg_it.next() {
size = arg_size
.parse::<usize>()
.expect("Size argument expects an integer value.");
} else {
panic!("No value specified for parameter size.");
}
}
Run Code Online (Sandbox Code Playgroud)
如果您想使用等号 ( =) 而不是空格来处理值,您可以在子句上方包含以下代码match并匹配键值:
let (key, value) = match arg.contains('=') {
true => {
let str_vec: Vec<&str> = arg.split('=').collect();
(String::from(str_vec[0]), Some(String::from(str_vec[1])))
},
false => {
(arg, None)
}
};
Run Code Online (Sandbox Code Playgroud)
从版本 0.8/0.9 开始,函数 args() 的正确路径是::std::os::args,即:
fn main() {
let args: ~[~str] = ::std::os::args();
println(args[0]);
}
Run Code Online (Sandbox Code Playgroud)
看来 Rust 现在即使使用标准 I/O 仍然非常不稳定,所以这可能很快就会过时。
| 归档时间: |
|
| 查看次数: |
40253 次 |
| 最近记录: |