Module option
Optional values.
Type [Option] represents an optional value: every [Option]
is either Some and contains a value, or None, and
does not. [Option] types are very common in Rust code, as
they have a number of uses:
- Initial values
- Return values for functions that are not defined over their entire input range (partial functions)
- Return value for otherwise reporting simple errors, where
Noneis returned on error - Optional struct fields
- Struct fields that can be loaned or "taken"
- Optional function arguments
- Nullable pointers
- Swapping things out of difficult situations
[Option]s are commonly paired with pattern matching to query the presence
of a value and take action, always accounting for the None case.
// The return value of the function is an option
let result = divide;
// Pattern match to retrieve the value
match result
Options and pointers ("nullable" pointers)
Rust's pointer types must always point to a valid location; there are
no "null" references. Instead, Rust has optional pointers, like
the optional owned box, [Option]<Box<T>>.
The following example uses [Option] to create an optional box of
i32. Notice that in order to use the inner i32 value, the
check_optional function first needs to use pattern matching to
determine whether the box has a value (i.e., it is Some(...)) or
not (None).
let optional = None;
check_optional;
let optional = Some;
check_optional;
The question mark operator, ?
Similar to the Result type, when writing code that calls many functions that return the
[Option] type, handling Some/None can be tedious. The question mark
operator, ?, hides some of the boilerplate of propagating values
up the call stack.
It replaces this:
#
With this:
#
It's much nicer!
Ending the expression with ? will result in the Some's unwrapped value, unless the
result is None, in which case None is returned early from the enclosing function.
? can be used in functions that return [Option] because of the
early return of None that it provides.
Representation
Rust guarantees to optimize the following types T such that [Option<T>]
has the same size, alignment, and function call ABI as T. It is
therefore sound, when T is one of these types, to transmute a value t of
type T to type Option<T> (producing the value Some(t)) and to
transmute a value Some(t) of type Option<T> to type T (producing the
value t).
In some of these cases, Rust further guarantees the following:
transmute::<_, Option<T>>([0u8; size_of::<T>()])is sound and producesOption::<T>::Nonetransmute::<_, [u8; size_of::<T>()]>(Option::<T>::None)is sound and produces[0u8; size_of::<T>()]
These cases are identified by the second column:
T |
Transmuting between [0u8; size_of::<T>()] and Option::<T>::None sound? |
|---|---|
Box<U> (specifically, only Box<U, Global>) |
when U: Sized |
&U |
when U: Sized |
&mut U |
when U: Sized |
fn, extern "C" fn1 |
always |
num::NonZero* |
always |
ptr::NonNull<U> |
when U: Sized |
#[repr(transparent)] struct around one of the types in this list. |
when it holds for the inner type |
Under some conditions the above types T are also null pointer optimized when wrapped in a Result.
This is called the "null pointer optimization" or NPO.
It is further guaranteed that, for the cases above, one can
mem::transmute from all valid values of T to Option<T> and
from Some::<T>(_) to T (but transmuting None::<T> to T
is undefined behavior).
Method overview
In addition to working with pattern matching, [Option] provides a wide
variety of different methods.
Querying the variant
The is_some and is_none methods return true if the [Option]
is Some or None, respectively.
The is_some_and and is_none_or methods apply the provided function
to the contents of the [Option] to produce a boolean value.
If this is None then a default result is returned instead without executing the function.
Adapters for working with references
as_refconverts from&[Option]<T>to[Option]<&T>as_mutconverts from&mut [Option]<T>to[Option]<&mut T>as_derefconverts from&[Option]<T>to[Option]<&T::Target>as_deref_mutconverts from&mut [Option]<T>to[Option]<&mut T::Target>as_pin_refconverts from[Pin]<&[Option]<T>>to[Option]<[Pin]<&T>>as_pin_mutconverts from[Pin]<&mut [Option]<T>>to[Option]<[Pin]<&mut T>>as_slicereturns a one-element slice of the contained value, if any. If this isNone, an empty slice is returned.as_mut_slicereturns a mutable one-element slice of the contained value, if any. If this isNone, an empty slice is returned.
Extracting the contained value
These methods extract the contained value in an [Option<T>] when it
is the Some variant. If the [Option] is None:
expectpanics with a provided custom messageunwrappanics with a generic messageunwrap_orreturns the provided default valueunwrap_or_defaultreturns the default value of the typeT(which must implement theDefaulttrait)unwrap_or_elsereturns the result of evaluating the provided functionunwrap_uncheckedproduces undefined behavior
Transforming contained values
These methods transform [Option] to [Result]:
ok_ortransformsSome(v)toOk(v), andNonetoErr(err)using the provided defaulterrvalueok_or_elsetransformsSome(v)toOk(v), andNoneto a value ofErrusing the provided functiontransposetransposes an [Option] of aResultinto aResultof an [Option]
These methods transform the Some variant:
filtercalls the provided predicate function on the contained valuetif the [Option] isSome(t), and returnsSome(t)if the function returnstrue; otherwise, returnsNoneflattenremoves one level of nesting from an [Option<Option<T>>]inspectmethod takes ownership of the [Option] and applies the provided function to the contained value by reference ifSomemaptransforms [Option<T>] to [Option<U>] by applying the provided function to the contained value ofSomeand leavingNonevalues unchanged
These methods transform [Option<T>] to a value of a possibly
different type U:
map_orapplies the provided function to the contained value ofSome, or returns the provided default value if the [Option] isNonemap_or_elseapplies the provided function to the contained value ofSome, or returns the result of evaluating the provided fallback function if the [Option] isNone
These methods combine the Some variants of two [Option] values:
zipreturnsSome((s, o))ifselfisSome(s)and the provided [Option] value isSome(o); otherwise, returnsNonezip_withcalls the provided functionfand returnsSome(f(s, o))ifselfisSome(s)and the provided [Option] value isSome(o); otherwise, returnsNone
Boolean operators
These methods treat the [Option] as a boolean value, where Some
acts like true and None acts like false. There are two
categories of these methods: ones that take an [Option] as input, and
ones that take a function as input (to be lazily evaluated).
The and, or, and xor methods take another [Option] as
input, and produce an [Option] as output. Only the and method can
produce an [Option<U>] value having a different inner type U than
[Option<T>].
| method | self | input | output |
|---|---|---|---|
and |
None |
(ignored) | None |
and |
Some(x) |
None |
None |
and |
Some(x) |
Some(y) |
Some(y) |
or |
None |
None |
None |
or |
None |
Some(y) |
Some(y) |
or |
Some(x) |
(ignored) | Some(x) |
xor |
None |
None |
None |
xor |
None |
Some(y) |
Some(y) |
xor |
Some(x) |
None |
Some(x) |
xor |
Some(x) |
Some(y) |
None |
The and_then and or_else methods take a function as input, and
only evaluate the function when they need to produce a new value. Only
the and_then method can produce an [Option<U>] value having a
different inner type U than [Option<T>].
| method | self | function input | function result | output |
|---|---|---|---|---|
and_then |
None |
(not provided) | (not evaluated) | None |
and_then |
Some(x) |
x |
None |
None |
and_then |
Some(x) |
x |
Some(y) |
Some(y) |
or_else |
None |
(not provided) | None |
None |
or_else |
None |
(not provided) | Some(y) |
Some(y) |
or_else |
Some(x) |
(not provided) | (not evaluated) | Some(x) |
This is an example of using methods like and_then and or in a
pipeline of method calls. Early stages of the pipeline pass failure
values (None) through unchanged, and continue processing on
success values (Some). Toward the end, or substitutes an error
message if it receives None.
# use BTreeMap;
let mut bt = new;
bt.insert;
bt.insert;
let res =
.into_iter
.map
.;
assert_eq!;
Comparison operators
If T implements PartialOrd then [Option<T>] will derive its
PartialOrd implementation. With this order, None compares as
less than any Some, and two Some compare the same way as their
contained values would in T. If T also implements
Ord, then so does [Option<T>].
assert!;
assert!;
Iterating over Option
An [Option] can be iterated over. This can be helpful if you need an
iterator that is conditionally empty. The iterator will either produce
a single value (when the [Option] is Some), or produce no values
(when the [Option] is None). For example, into_iter acts like
once(v) if the [Option] is Some(v), and like empty() if
the [Option] is None.
Iterators over [Option<T>] come in three types:
into_iterconsumes the [Option] and produces the contained valueiterproduces an immutable reference of type&Tto the contained valueiter_mutproduces a mutable reference of type&mut Tto the contained value
An iterator over [Option] can be useful when chaining iterators, for
example, to conditionally insert items. (It's not always necessary to
explicitly call an iterator constructor: many Iterator methods that
accept other iterators will also accept iterable types that implement
IntoIterator, which includes [Option].)
let yep = Some;
let nope = None;
// chain() already calls into_iter(), so we don't have to do so
let nums: = .chain.chain.collect;
assert_eq!;
let nums: = .chain.chain.collect;
assert_eq!;
One reason to chain iterators in this way is that a function returning
impl Iterator must have all possible return values be of the same
concrete type. Chaining an iterated [Option] can help with that.
println!;
println!;
If we try to do the same thing, but using once() and empty(),
we can't return impl Iterator anymore because the concrete types of
the return values differ.
# use std::iter::{empty, once};
// This won't compile because all possible returns from the function
// must have the same concrete type.
fn make_iter(do_insert: bool) -> impl Iterator<Item = i32> {
// Explicit returns to illustrate return types not matching
match do_insert {
true => return (0..4).chain(once(42)).chain(4..8),
false => return (0..4).chain(empty()).chain(4..8),
}
}
Collecting into Option
[Option] implements the FromIterator trait,
which allows an iterator over [Option] values to be collected into an
[Option] of a collection of each contained value of the original
[Option] values, or None if any of the elements was None.
let v = ;
let res: = v.into_iter.collect;
assert_eq!;
let v = ;
let res: = v.into_iter.collect;
assert_eq!;
[Option] also implements the Product and
Sum traits, allowing an iterator over [Option] values
to provide the [product][Iterator::product] and
[sum][Iterator::sum] methods.
let v = ;
let res: = v.into_iter.sum;
assert_eq!;
let v = ;
let res: = v.into_iter.product;
assert_eq!;
Modifying an [Option] in-place
These methods return a mutable reference to the contained value of an
[Option<T>]:
insertinserts a value, dropping any old contentsget_or_insertgets the current value, inserting a provided default value if it isNoneget_or_insert_defaultgets the current value, inserting the default value of typeT(which must implementDefault) if it isNoneget_or_insert_withgets the current value, inserting a default computed by the provided function if it isNone
These methods transfer ownership of the contained value of an
[Option]:
taketakes ownership of the contained value of an [Option], if any, replacing the [Option] withNonereplacetakes ownership of the contained value of an [Option], if any, replacing the [Option] with aSomecontaining the provided value
Examples
Basic pattern matching on [Option]:
let msg = Some;
// Take a reference to the contained string
if let Some = &msg
// Remove the contained string, destroying the Option
let unwrapped_msg = msg.unwrap_or;
Initialize a result to None before a loop:
// A list of data to search through.
let all_the_big_things = ;
// We're going to search for the name of the biggest animal,
// but to start with we've just got `None`.
let mut name_of_biggest_animal = None;
let mut size_of_biggest_animal = 0;
for big_thing in &all_the_big_things
match name_of_biggest_animal
-
this remains true for
unsafevariants, any argument/return types, and any other ABI:[unsafe] extern "abi" fn(e.g.,extern "system" fn) ↩
Structs
-
IntoIter
An iterator over the value in
Somevariant of anOption. -
Iter
An iterator over a reference to the
Somevariant of anOption. -
IterMut
An iterator over a mutable reference to the
Somevariant of anOption. -
OptionFlatten
The iterator produced by
Option::into_flat_iter. See its documentation for more.
Enums
-
Option
The
Optiontype. See the module level documentation for more.