Rust: Functions
What you will learn
How to define functions, how the last expression acts as an implicit return, and the difference between statements and expressions.
Defining a function
fn greet(name: &str) -> String {
format!("Hello, {}!", name) // no semicolon = return
}
Syntax: fn keyword, function name, parameters in parentheses with types, -> return type, body in { }. Notice the last expression has no semicolon -- that's the implicit return.
Expression vs statement
This is a key Rust concept:
- Expression: evaluates to a value.
x + 1,func_call(), a block{ let y = 2; y * 2 }. - Statement: performs an action but produces no value.
let x = 5;is a statement.
fn add(a: i32, b: i32) -> i32 {
a + b // expression -- returned
}
fn add_with_return(a: i32, b: i32) -> i32 {
return a + b; // also works but less idiomatic
}
The println! macro
fn main() {
let name = "Alice";
println!("Hello, {}!", name); // macro -- note the !
println!("{name}"); // Rust 1.58+ inline
}
Early returns with return
fn factorial(n: u32) -> u32 {
if n == 0 {
return 1; // early return
}
n * factorial(n - 1) // implicit return
}
Common mistakes
- Adding a semicolon to the last expression -- that turns it into a statement, and the function returns
()(unit) instead - Forgetting the type annotation on function parameters -- Rust requires explicit parameter types
- Confusing
!(macro) with function calls -- seeprintln!,format!,vec!
Quick check below!