What are Command Line Arguments?
Command-line arguments are extra input values provided to a program when it is run from a terminal. These inputs are passed after the program name and are typically used to configure how the program behaves.
Example: Command-Line Input
$ my_program arg1 arg2 arg3
- Here, arg1, arg2 and arg3 are command-line arguments passed to the program my_program.
Why Use Command Line Arguments in Rust?
Command-line arguments make programs:
- Dynamic: Modify program behavior without changing code.
- Flexible: Process user-specific inputs like filenames or options.
- Interactive: Enable lightweight configuration for tools and scripts.
How to Handle Command Line Arguments in Rust
Rust’s std::env
module provides the args
function to retrieve command-line arguments. The arguments are returned as an iterator, which can be collected into a vector for easier processing.
1. Getting Command Line Arguments
The std::env::args() function captures all arguments, including the program name itself.
Example: Retrieving Command-Line Arguments
use std::env;
fn main() {
let args: Vec<String> = env::args().collect();
println!("Arguments:");
for arg in args {
println!("{}", arg);
}
}
Explanation:
- env::args() returns an iterator over the command-line arguments.
- collect() converts the iterator into a Vec<String>.
- The first argument (args[0]) is the program name, and subsequent arguments are user-provided.
Output Example:
$ cargo run hello world
Arguments:
target/debug/my_program
hello
world
2. Ignoring the Program Name
If you’re only interested in the user-provided arguments, skip the first element of the args vector.
Example: Ignoring the Program Name
use std::env;
fn main() {
let args: Vec<String> = env::args().skip(1).collect();
println!("User-provided Arguments:");
for arg in args {
println!("{}", arg);
}
}
Explanation:
- skip(1) ignores the first argument (program name).
3. Accessing Specific Arguments
You can access arguments by their position in the vector.
Example: Accessing Specific Arguments
use std::env;
fn main() {
let args: Vec<String> = env::args().collect();
if args.len() > 1 {
println!("First Argument: {}", args[1]);
} else {
println!("No arguments provided!");
}
}
Output Examples:
With Arguments:
$ cargo run hello
First Argument: hello
Without Arguments:
$ cargo run
No arguments provided!
4. Handling Missing or Invalid Arguments
Always validate arguments to handle cases where users provide too few or incorrect inputs.
Example: Validating Arguments
use std::env;
fn main() {
let args: Vec<String> = env::args().collect();
if args.len() != 3 {
eprintln!("Usage: {} <arg1> <arg2>", args[0]);
return;
}
let arg1 = &args[1];
let arg2 = &args[2];
println!("Argument 1: {}", arg1);
println!("Argument 2: {}", arg2);
}
Output Examples:
Correct Usage:
$ cargo run hello world
Argument 1: hello
Argument 2: world
Incorrect Usage:
$ cargo run hello
Usage: target/debug/my_program <arg1> <arg2>
5. Parsing Numeric Arguments
If arguments are expected to be numbers, convert them using parse() and handle potential errors.
Example: Parsing Numbers
use std::env;
fn main() {
let args: Vec<String> = env::args().collect();
if args.len() != 3 {
eprintln!("Usage: {} <num1> <num2>", args[0]);
return;
}
let num1: i32 = args[1].parse().expect("Please provide a valid number for num1");
let num2: i32 = args[2].parse().expect("Please provide a valid number for num2");
println!("Sum: {}", num1 + num2);
}
Output Example:
$ cargo run 10 20
Sum: 30
6. Using External Crates for Advanced Parsing
For complex command-line arguments, use crates like clap or structopt. These provide features like named flags and default values.
Example: Using clap for Named Arguments
# Add this to Cargo.toml
[dependencies]
clap = { version = "4.0", features = ["derive"] }
use clap::Parser;
/// A simple program to demonstrate named arguments
#[derive(Parser)]
struct Cli {
/// The first argument
arg1: String,
/// The second argument
arg2: String,
}
fn main() {
let args = Cli::parse();
println!("Argument 1: {}", args.arg1);
println!("Argument 2: {}", args.arg2);
}
Output Example:
$ cargo run -- hello world
Argument 1: hello
Argument 2: world