Async/Await Basics
async and .await let a program pause one task while waiting for something slow, and get on with other work in the meantime.In this page:
Declaring an Async Function
An async fn looks like a normal function but returns a Future representing its eventual result, rather than running its body immediately when called. Async syntax needs the 2018+ Rust edition and a runtime to actually execute, so this snippet shows the shape as a comment and demonstrates the underlying idea (a value that isn't ready immediately) with plain std code.
Example: Declaring an Async Function
// Async syntax (needs edition 2018+ and a runtime), shown conceptually:
// async fn compute() -> i32 {
// 42
// }
fn main() {
println!("async fn compute() would return a Future, not an i32 directly");
println!("It must be awaited inside an async runtime to actually run");
}
Login to try C/C++/Java/PHP code in the editor
The Role of .await
Inside an async context, .await is used on a Future to drive it to completion, pausing that task (without blocking the whole program) until the value is ready. Since .await requires edition 2018+ and a runtime, this snippet keeps the async shape as a comment and shows the conceptual chaining with plain function calls instead.
Example: The Role of .await
// Conceptual async chain (needs edition 2018+ and a runtime):
// async fn get_value() -> i32 { 10 }
// async fn use_value() -> i32 {
// let v = get_value().await;
// v + 1
// }
fn get_value() -> i32 {
10
}
fn use_value() -> i32 {
let v = get_value();
v + 1
}
fn main() {
println!("Synchronous stand-in result: {}", use_value());
println!("An async version would use .await instead of a direct call");
}
Login to try C/C++/Java/PHP code in the editor
Why Async Needs a Runtime
The Rust standard library defines the Future trait and async/.await syntax, but does not include an executor to actually run futures -- that job belongs to a runtime crate such as Tokio or async-std.
Example: Why Async Needs a Runtime
fn main() {
println!("The standard library defines Future and async/.await syntax");
println!("But executing futures requires an external runtime crate");
println!("Common choices: tokio, async-std");
}
Login to try C/C++/Java/PHP code in the editor
Async Is for Concurrency, Not Parallelism
Async/await shines when a program is waiting on many slow I/O operations (like network requests) at once, letting a single thread juggle them efficiently, rather than for speeding up raw CPU-bound computation.
Example: Async Is for Concurrency, Not Parallelism
fn main() {
println!("Async excels at juggling many waiting I/O tasks concurrently");
println!("For CPU-bound parallel work, OS threads are usually the better tool");
}
Login to try C/C++/Java/PHP code in the editor
- Assuming an
async fnruns immediately when called -- it actually returns a lazyFuturethat does nothing until it is awaited or polled. - Trying to run async code without an async runtime (like Tokio or async-std) actually driving the futures to completion.
- Forgetting
.awaitcan only be used inside anasync fnor async block, not in ordinary synchronous code.
- An
async fnreturns aFutureimmediately, representing work that hasn't started yet. .awaitdrives aFuturetoward completion, yielding control back to the runtime while it waits.- Async code needs a runtime (like Tokio) to actually execute the futures it produces -- the standard library alone doesn't run them.
- Async/await is designed for efficiently waiting on many I/O-bound tasks concurrently, not for CPU-bound parallelism.
Chapter Quiz — Complete all 6 topics to unlock
0/6 topics done
Complete these topics first: