The Rust Reference › Debugger attributes › The `debugger_visualizer` attribute › Using `debugger_visualizer` with Natvis

```xml
<?xml version="1.0" encoding="utf-8"?>
<AutoVisualizer xmlns="http://schemas.microsoft.com/vstudio/debugger/natvis/2010">
    <Type Name="foo::FancyRect">
      <DisplayString>({x},{y}) + ({dx}, {dy})</DisplayString>
      <Expand>
        <Synthetic Name="LowerLeft">
          <DisplayString>({x}, {y})</DisplayString>
        </Synthetic>
        <Synthetic Name="UpperLeft">
          <DisplayString>({x}, {y + dy})</DisplayString>
        </Synthetic>
        <Synthetic Name="UpperRight">
          <DisplayString>({x + dx}, {y + dy})</DisplayString>
        </Synthetic>
        <Synthetic Name="LowerRight">
          <DisplayString>({x + dx}, {y})</DisplayString>
        </Synthetic>
      </Expand>
    </Type>
</AutoVisualizer>
```
When viewed under WinDbg, the `fancy_rect` variable would be shown as follows:
```text
Variables:
fancy_rect: (10.0, 10.0) + (5.0, 5.0)
LowerLeft: (10.0, 10.0)
UpperLeft: (10.0, 15.0)
UpperRight: (15.0, 15.0)
LowerRight: (15.0, 10.0)
```


The Rust Reference › Debugger attributes › The `debugger_visualizer` attribute › Using `debugger_visualizer` with GDB

GDB supports the use of a structured Python script, called a *pretty printer*, that describes how a type should be visualized in the debugger view. For detailed information on pretty printers, refer to GDB's [pretty printing documentation].
Embedded pretty printers are not automatically loaded when debugging a binary under GDB.
There are two ways to enable auto-loading embedded pretty printers:
1. Launch GDB with extra arguments to explicitly add a directory or binary to the auto-load safe path: `gdb -iex "add-auto-load-safe-path safe-path path/to/binary" path/to/binary` For more information, see GDB's [auto-loading documentation].
1. Create a file named `gdbinit` under `$HOME/.config/gdb` (you may need to create the directory if it doesn't already exist). Add the following line to that file: `add-auto-load-safe-path path/to/binary`.
These scripts are embedded using the `gdb_script_file` key, which is a path relative to the source file.
```rust ignore
#![debugger_visualizer(gdb_script_file = "printer.py")]

struct Person {
    name: String,
    age: i32,
}

fn main() {
    let bob = Person { name: String::from("Bob"), age: 10 };
    println!("set breakpoint here");
}
```
`printer.py` contains:

Debugger attributes
The `debugger_visualizer` attribute
Using `debugger_visualizer` with GDB


The Rust Reference › Debugger attributes › The `debugger_visualizer` attribute › Using `debugger_visualizer` with GDB

```python
import gdb

class PersonPrinter:
    "Print a Person"

    def __init__(self, val):
        self.val = val
        self.name = val["name"]
        self.age = int(val["age"])

    def to_string(self):
        return "{} is {} years old.".format(self.name, self.age)

def lookup(val):
    lookup_tag = val.type.tag
    if lookup_tag is None:
        return None
    if "foo::Person" == lookup_tag:
        return PersonPrinter(val)

    return None

gdb.current_objfile().pretty_printers.append(lookup)
```
When the crate's debug executable is passed into GDB[^rust-gdb], `print bob` will display:
```text
"Bob" is 10 years old.
```
[^rust-gdb]: Note: This assumes you are using the `rust-gdb` script which configures pretty-printers for standard library types like `String`.


The Rust Reference › Debugger attributes › The `collapse_debuginfo` attribute

The *`collapse_debuginfo` [attribute]* controls whether code locations from a macro definition are collapsed into a single location associated with the macro's call site when generating debuginfo for code calling this macro.
```rust
#[collapse_debuginfo(yes)]
macro_rules! example {
    () => {
        println!("hello!");
    };
}
```
When using a debugger, invoking the `example` macro may appear as though it is calling a function. That is, when you step to the invocation site, it may show the macro invocation rather than the expanded code.
The syntax for the `collapse_debuginfo` attribute is:
```grammar,attributes
@root CollapseDebuginfoAttribute -> `collapse_debuginfo` `(` CollapseDebuginfoOption `)`

CollapseDebuginfoOption ->
      `yes`
    | `no`
    | `external`
```
The `collapse_debuginfo` attribute may only be applied to a [`macro_rules` definition].
The `collapse_debuginfo` attribute may used only once on a macro.
The `collapse_debuginfo` attribute accepts these options:
- `#[collapse_debuginfo(yes)]` --- Code locations in debuginfo are collapsed.
- `#[collapse_debuginfo(no)]` --- Code locations in debuginfo are not collapsed.
- `#[collapse_debuginfo(external)]` --- Code locations in debuginfo are collapsed only if the macro comes from a different crate.
The `external` behavior is the default for macros that don't have this attribute unless they are built-in macros. For built-in macros the default is `yes`.
`rustc` has a [`-C collapse-macro-debuginfo`] CLI option to override both the default behavior and the values of any `#[collapse_debuginfo]` attributes.

Debugger attributes
The `collapse_debuginfo` attribute


The Rust Reference › Statements and expressions

Rust is _primarily_ an expression language. This means that most forms of value-producing or effect-causing evaluation are directed by the uniform syntax category of _expressions_. Each kind of expression can typically _nest_ within each other kind of expression, and rules for evaluation of expressions involve specifying both the value produced by the expression and the order in which its sub-expressions are themselves evaluated.
In contrast, statements serve _mostly_ to contain and explicitly sequence expression evaluation.


The Rust Reference › Statements

```grammar,statements
Statement ->
      `;`
    | Item
    | LetStatement
    | ExpressionStatement
    | OuterAttribute* MacroInvocationSemi
```
A *statement* is a component of a [block], which is in turn a component of an outer [expression] or [function].
Rust has two kinds of statement: declaration statements and expression statements.


The Rust Reference › Statements › Declaration statements

A *declaration statement* is one that introduces one or more *names* into the enclosing statement block. The declared names may denote new variables or new items.
The two kinds of declaration statements are item declarations and `let` statements.


The Rust Reference › Statements › Declaration statements › Item declarations

An *item declaration statement* has a syntactic form identical to an item declaration within a [module].
Declaring an item within a statement block restricts its [scope] to the block containing the statement. The item is not given a [canonical path] nor are any sub-items it may declare.
The exception to this is that associated items defined by [implementations] are still accessible in outer scopes as long as the item and, if applicable, trait are accessible. It is otherwise identical in meaning to declaring the item inside a module.
There is no implicit capture of the containing function's generic parameters, parameters, and local variables. For example, `inner` may not access `outer_var`.
```rust
fn outer() {
  let outer_var = true;

  fn inner() { /* outer_var is not in scope here */ }

  inner();
}
```

Statements
Declaration statements
Item declarations


The Rust Reference › Statements › Declaration statements › `let` statements

```grammar,statements
LetStatement ->
    OuterAttribute* `let` PatternNoTopAlt ( `:` Type )?
    (
          `=` Expression
        | `=` Expression _except [LazyBooleanExpression] or end with a `}`_
              `else` BlockExpressionNoInnerAttributes
    )? `;`
```
A *`let` statement* introduces a new set of [variables], given by a [pattern]. The pattern is followed optionally by a type annotation and then either ends, or is followed by an initializer expression plus an optional `else` block.
When no type annotation is given, the compiler will infer the type, or signal an error if insufficient type information is available for definite inference.
Any variables introduced by a variable declaration are visible from the point of declaration until the end of the enclosing block scope, except when they are shadowed by another variable declaration.
If an `else` block is not present, the pattern must be irrefutable. If an `else` block is present, the pattern may be refutable.
If the pattern does not match (this requires it to be refutable), the `else` block is executed. The `else` block must always diverge (evaluate to the [never type]).
```rust
let (mut v, w) = (vec![1, 2, 3], 42); // The bindings may be mut or const
let Some(t) = v.pop() else { // Refutable patterns require an else block
    panic!(); // The else block must diverge
};
let [u, v] = [v[0], v[1]] else { // This pattern is irrefutable, so the compiler
                                 // will lint as the else block is redundant.
    panic!();
};
```

Statements
Declaration statements
`let` statements


The Rust Reference › Statements › Expression statements

```grammar,statements
ExpressionStatement ->
      ExpressionWithoutBlock `;`
    | ExpressionWithBlock `;`?
```
An *expression statement* is one that evaluates an [expression] and ignores its result. As a rule, an expression statement's purpose is to trigger the effects of evaluating its expression.
An expression that consists of only a block expression or control flow expression, if used in a context where a statement is permitted, can omit the trailing semicolon. This can cause an ambiguity between it being parsed as a standalone statement and as a part of another expression; in this case, it is parsed as a statement.
The type of [ExpressionWithBlock] expressions when used as statements must be the unit type.
```rust
v.pop();          // Ignore the element returned from pop
if v.is_empty() {
    v.push(5);
} else {
    v.remove(0);
}                 // Semicolon can be omitted.
[1];              // Separate expression statement, not an indexing expression.
```
When the trailing semicolon is omitted, the result must be type `()`.
```rust
// bad: the block's type is i32, not ()
// Error: expected `()` because of default return type
// if true {
//   1
// }

// good: the block's type is i32
if true {
  1
} else {
  2
};
```


The Rust Reference › Statements › Attributes on statements

Statements accept [outer attributes]. The attributes that have meaning on a statement are [`cfg`], and [the lint check attributes].


The Rust Reference › Expressions

```grammar,expressions
Expression ->
      ExpressionWithoutBlock
    | ExpressionWithBlock

ExpressionWithoutBlock ->
    OuterAttribute* ExpressionWithoutBlockNoAttrs

ExpressionWithoutBlockNoAttrs ->
      LiteralExpression
    | PathExpression
    | OperatorExpression
    | GroupedExpression
    | ArrayExpression
    | AwaitExpression
    | IndexExpression
    | TupleExpression
    | TupleIndexingExpression
    | StructExpression
    | CallExpression
    | MethodCallExpression
    | FieldExpression
    | ClosureExpression
    | AsyncBlockExpression
    | ContinueExpression
    | BreakExpression
    | RangeExpression
    | ReturnExpression
    | UnderscoreExpression
    | MacroInvocation

ExpressionWithBlock ->
    OuterAttribute* ExpressionWithBlockNoAttrs

ExpressionWithBlockNoAttrs ->
      BlockExpression
    | ConstBlockExpression
    | UnsafeBlockExpression
    | LoopExpression
    | IfExpression
    | MatchExpression
```
An expression may have two roles: it always produces a *value*, and it may have *effects* (otherwise known as "side effects").
An expression *evaluates to* a value, and has effects during *evaluation*.
Many expressions contain sub-expressions, called the *operands* of the expression.
The meaning of each kind of expression dictates several things:
* Whether or not to evaluate the operands when evaluating the expression
* The order in which to evaluate the operands
* How to combine the operands' values to obtain the value of the expression
In this way, the structure of expressions dictates the structure of execution. Blocks are just another kind of expression, so blocks, statements, expressions, and blocks again can recursively nest inside each other to an arbitrary depth.
We give names to the operands of expressions so that we may discuss them, but these names are not stable and may be changed.


The Rust Reference › Expressions › Expression precedence

The precedence of Rust operators and expressions is ordered as follows, going from strong to weak. Binary Operators at the same precedence level are grouped in the order given by their associativity.


The Rust Reference › Expressions › Expression precedence

| Operator/Expression         | Associativity       |
|-----------------------------|---------------------|
| Paths          |                     |
| Method calls |                     |
| Field expressions | left to right   |
| Function calls, array indexing | |
| `?`             |                     |
| Unary `-` `!` `*` borrow | |
| `as`             | left to right       |
| `*` `/` `%` | left to right       |
| `+` `-` | left to right       |
| `<<` `>>` | left to right     |
| `&`     | left to right       |
| `^`     | left to right       |
| | | left to right       |
| `==` `!=` `<` `>` `<=` `>=` | Require parentheses |
| `&&`     | left to right       |
| || | left to right       |
| `..` `..=` | Require parentheses |
| `=` `+=` `-=` `*=` `/=` `%=`
 `&=` |= `^=` `<<=` `>>=` | right to left |
| `return` `break` closures  | |


The Rust Reference › Expressions › Evaluation order of operands

The following list of expressions all evaluate their operands the same way, as described after the list. Other expressions either don't take operands or evaluate them conditionally as described on their respective pages.
* Dereference expression
* Error propagation expression
* Negation expression
* Arithmetic and logical binary operators
* Comparison operators
* Type cast expression
* Grouped expression
* Array expression
* Await expression
* Index expression
* Tuple expression
* Tuple index expression
* Struct expression
* Call expression
* Method call expression
* Field expression
* Break expression
* Range expression
* Return expression
The operands of these expressions are evaluated prior to applying the effects of the expression. Expressions taking multiple operands are evaluated left to right as written in the source code.
Which subexpressions are the operands of an expression is determined by expression precedence as per the previous section.
For example, the two `next` method calls will always be called in the same order:
```rust
let mut one_two = vec![1, 2].into_iter();
assert_eq!(
    (1, 2),
    (one_two.next().unwrap(), one_two.next().unwrap())
);
```
Since this is applied recursively, these expressions are also evaluated from innermost to outermost, ignoring siblings until there are no inner subexpressions.

Expressions
Evaluation order of operands


The Rust Reference › Expressions › Place expressions and value expressions

Expressions are divided into two main categories: place expressions and value expressions; there is also a third, minor category of expressions called assignee expressions. Within each expression, operands may likewise occur in either place context or value context. The evaluation of an expression depends both on its own category and the context it occurs within.
A *place expression* is an expression that represents a memory location.
These expressions are [paths] which refer to local variables, [static variables], dereferences (`*expr`), [array indexing] expressions (`expr[expr]`), [field] references (`expr.f`) and parenthesized place expressions.
All other expressions are value expressions.
A *value expression* is an expression that represents an actual value.
The following contexts are *place expression* contexts:
* The left operand of a [compound assignment] expression.
* The operand of a unary [borrow], [raw borrow] or dereference operator.
* The operand of a [field expression].
* The indexed operand of an [array indexing expression].
* The tuple operand of a [tuple indexing expression].
* The operand of any [implicit borrow].
* The initializer of a [let statement].
* The [scrutinee] of an [`if let`], `match`, or [`while let`] expression.
* The base of a [functional update] struct expression.
Historically, place expressions were called *lvalues* and value expressions were called *rvalues*.
An *assignee expression* is an expression that appears in the left operand of an assignment expression. Explicitly, the assignee expressions are:

Expressions
Place expressions and value expressions


The Rust Reference › Expressions › Place expressions and value expressions

- Place expressions.
- [Underscores].
- [Tuples] of assignee expressions.
- Slices of assignee expressions.
- [Tuple structs] of assignee expressions.
- [Structs] of assignee expressions (with optionally named fields).
- [Unit structs]
Arbitrary parenthesisation is permitted inside assignee expressions.


The Rust Reference › Expressions › Place expressions and value expressions › Moved and copied types

When a place expression is evaluated in a value expression context, or is bound by value in a pattern, it denotes the value held _in_ that memory location.
If the type of that value implements [`Copy`], then the value will be copied.
In the remaining situations, if that type is [`Sized`], then it may be possible to move the value.
Only the following place expressions may be moved out of:
* [Variables] which are not currently borrowed.
* Temporary values.
* Fields of a place expression which can be moved out of and don't implement [`Drop`].
* The result of dereferencing an expression with type [`Box<T>`] and that can also be moved out of.
After moving out of a place expression that evaluates to a local variable, the location is deinitialized and cannot be read from again until it is reinitialized.
In all other cases, trying to use a place expression in a value expression context is an error.

Expressions
Place expressions and value expressions
Moved and copied types


The Rust Reference › Expressions › Place expressions and value expressions › Mutability

For a place expression to be assigned to, mutably borrowed, [implicitly mutably borrowed], or bound to a pattern containing `ref mut`, it must be _mutable_. We call these *mutable place expressions*. In contrast, other place expressions are called *immutable place expressions*.
The following expressions can be mutable place expression contexts:
* Mutable [variables] which are not currently borrowed.
* [Mutable `static` items].
* [Temporary values].
* Fields: this evaluates the subexpression in a mutable place expression context.
* Dereferences of a `*mut T` pointer.
* Dereference of a variable, or field of a variable, with type `&mut T`. Note: This is an exception to the requirement of the next rule.
* Dereferences of a type that implements `DerefMut`: this then requires that the value being dereferenced is evaluated in a mutable place expression context.
* [Array indexing] of a type that implements `IndexMut`: this then evaluates the value being indexed, but not the index, in mutable place expression context.

Expressions
Place expressions and value expressions
Mutability


The Rust Reference › Expressions › Place expressions and value expressions › Temporaries

When using a value expression in most place expression contexts, a temporary unnamed memory location is created and initialized to that value. The expression evaluates to that location instead, except if [promoted] to a `static`. The [drop scope] of the temporary is usually the end of the enclosing statement.

Expressions
Place expressions and value expressions
Temporaries


The Rust Reference › Expressions › Place expressions and value expressions › Super macros › `format_args!`

Certain built-in macros may create [temporaries] whose scopes may be [extended]. These temporaries are *super temporaries* and these macros are *super macros*. Invocations of these macros are *super macro call expressions*. Arguments to these macros may be *super operands*.
When a super macro call expression is an [extending expression], its super operands are [extending expressions] and the scopes of the super temporaries are [extended]. See [destructors.scope.lifetime-extension.exprs].
Except for the format string argument, all arguments passed to [`format_args!`] are *super operands*.
```rust,edition2024
// Due to the call being an extending expression and the argument
// being a super operand, the inner block is an extending expression,
// so the scope of the temporary created in its trailing expression
// is extended.
let _ = format_args!("{}", { &temp() }); // OK
```
The super operands of [`format_args!`] are [implicitly borrowed] and are therefore [place expression contexts]. When a [value expression] is passed as an argument, it creates a *super temporary*.
```rust
let x = format_args!("{}", temp());
x; // <-- The temporary is extended, allowing use here.
```
The expansion of a call to [`format_args!`] sometimes creates other internal *super temporaries*.
```rust,compile_fail,E0716
let x = {
    // This call creates an internal temporary.
    let x = format_args!("{:?}", 0);
    x // <-- The temporary is extended, allowing its use here.
}; // <-- The temporary is dropped here.
x; // ERROR
```
```rust
// This call doesn't create an internal temporary.
let x = { let x = format_args!("{}", 0); x };
x; // OK
```

Expressions
Place expressions and value expressions
Super macros
`format_args!`


The Rust Reference › Expressions › Place expressions and value expressions › Super macros › `pin!`

The details of when [`format_args!`] does or does not create internal temporaries are currently unspecified.
The argument to [`pin!`] is a *super operand*.
```rust,edition2024
// As above for `format_args!`.
let _ = pin!({ &temp() }); // OK
```
The argument to [`pin!`] is a [value expression context] and creates a *super temporary*.
```rust
// The argument is evaluated into a super temporary.
let x = pin!(temp());
// The temporary is extended, allowing its use here.
x; // OK
```

Expressions
Place expressions and value expressions
Super macros
`pin!`


The Rust Reference › Expressions › Place expressions and value expressions › Implicit borrows

Certain expressions will treat an expression as a place expression by implicitly borrowing it. For example, it is possible to compare two unsized slices for equality directly, because the `==` operator implicitly borrows its operands:
```rust
let a: &[i32];
let b: &[i32];
// ...
*a == *b;
// Equivalent form:
::std::cmp::PartialEq::eq(&*a, &*b);
```
Implicit borrows may be taken in the following expressions:
* Left operand in [method-call] expressions.
* Left operand in [field] expressions.
* Left operand in [call expressions].
* Left operand in [array indexing] expressions.
* Operand of the dereference operator (`*`).
* Operands of [comparison].
* Left operands of the [compound assignment].
* Arguments to [`format_args!`] except the format string.

Expressions
Place expressions and value expressions
Implicit borrows


The Rust Reference › Expressions › Overloading traits

Many of the following operators and expressions can also be overloaded for other types using traits in `std::ops` or `std::cmp`. These traits also exist in `core::ops` and `core::cmp` with the same names.


The Rust Reference › Expressions › Expression attributes

[Outer attributes] before an expression are allowed only in a few specific cases:
* Before an expression used as a [statement].
* Elements of [array expressions], [tuple expressions], [call expressions], and tuple-style [struct] expressions.
* The tail expression of [block expressions].
They are never allowed before:
* [Range] expressions.
* Binary operator expressions ([ArithmeticOrLogicalExpression], [ComparisonExpression], [LazyBooleanExpression], [TypeCastExpression], [AssignmentExpression], [CompoundAssignmentExpression]).


The Rust Reference › Literal expressions

```grammar,expressions
LiteralExpression ->
      CHAR_LITERAL
    | STRING_LITERAL
    | RAW_STRING_LITERAL
    | BYTE_LITERAL
    | BYTE_STRING_LITERAL
    | RAW_BYTE_STRING_LITERAL
    | C_STRING_LITERAL
    | RAW_C_STRING_LITERAL
    | INTEGER_LITERAL
    | FLOAT_LITERAL
    | `true`
    | `false`
```
A _literal expression_ is an expression consisting of a single token, rather than a sequence of tokens, that immediately and directly denotes the value it evaluates to, rather than referring to it by name or some other evaluation rule.
A literal is a form of [constant expression], so is evaluated (primarily) at compile time.
Each of the lexical literal forms described earlier can make up a literal expression, as can the keywords `true` and `false`.
```rust
"hello";   // string type
'5';       // character type
5;         // integer type
```
In the descriptions below, the _string representation_ of a token is the sequence of characters from the input which matched the token's production in a *Lexer* grammar snippet.
This string representation never includes a character `U+000D` (CR) immediately followed by `U+000A` (LF): this pair would have been previously transformed into a single `U+000A` (LF).


The Rust Reference › Literal expressions › Escapes

The descriptions of textual literal expressions below make use of several forms of _escape_.
Each form of escape is characterised by:
 * an _escape sequence_: a sequence of characters, which always begins with `U+005C` (`\`)
 * an _escaped value_: either a single character or an empty sequence of characters
In the definitions of escapes below:
 * An _octal digit_ is any of the characters in the range \[`0`-`7`].
 * A _hexadecimal digit_ is any of the characters in the ranges \[`0`-`9`], \[`a`-`f`], or \[`A`-`F`].


The Rust Reference › Literal expressions › Escapes › Simple escapes

Each sequence of characters occurring in the first column of the following table is an escape sequence.
In each case, the escaped value is the character given in the corresponding entry in the second column.
| Escape sequence | Escaped value            |
|-----------------|--------------------------|
| `\0`            | U+0000 (NUL)             |
| `\t`            | U+0009 (HT)              |
| `\n`            | U+000A (LF)              |
| `\r`            | U+000D (CR)              |
| `\"`            | U+0022 (QUOTATION MARK)  |
| `\'`            | U+0027 (APOSTROPHE)      |
| `\\`            | U+005C (REVERSE SOLIDUS) |

Literal expressions
Escapes
Simple escapes


The Rust Reference › Literal expressions › Escapes › 8-bit escapes

The escape sequence consists of `\x` followed by two hexadecimal digits.
The escaped value is the character whose [Unicode scalar value] is the result of interpreting the final two characters in the escape sequence as a hexadecimal integer, as if by [`u8::from_str_radix`] with radix 16.
The escaped value therefore has a [Unicode scalar value] in the range of `u8`.

Literal expressions
Escapes
8-bit escapes


The Rust Reference › Literal expressions › Escapes › 7-bit escapes

The escape sequence consists of `\x` followed by an octal digit then a hexadecimal digit.
The escaped value is the character whose [Unicode scalar value] is the result of interpreting the final two characters in the escape sequence as a hexadecimal integer, as if by [`u8::from_str_radix`] with radix 16.

Literal expressions
Escapes
7-bit escapes


The Rust Reference › Literal expressions › Escapes › Unicode escapes

The escape sequence consists of `\u{`, followed by a sequence of characters each of which is a hexadecimal digit or `_`, followed by `}`.
The escaped value is the character whose [Unicode scalar value] is the result of interpreting the hexadecimal digits contained in the escape sequence as a hexadecimal integer, as if by [`u32::from_str_radix`] with radix 16.
The permitted forms of a [CHAR_LITERAL] or [STRING_LITERAL] token ensure that there is such a character.

Literal expressions
Escapes
Unicode escapes


The Rust Reference › Literal expressions › Escapes › String continuation escapes

The escape sequence consists of `\` followed immediately by `U+000A` (LF), and all following whitespace characters before the next non-whitespace character. For this purpose, the whitespace characters are `U+0009` (HT), `U+000A` (LF), `U+000D` (CR), and `U+0020` (SPACE).
The escaped value is an empty sequence of characters.
The effect of this form of escape is that a string continuation skips following whitespace, including additional newlines. Thus `a`, `b` and `c` are equal:
```rust
let a = "foobar";
let b = "foo\
         bar";
let c = "foo\

     bar";

assert_eq!(a, b);
assert_eq!(b, c);
```
Skipping additional newlines (as in example c) is potentially confusing and unexpected. This behavior may be adjusted in the future. Until a decision is made, it is recommended to avoid relying on skipping multiple newlines with line continuations. See this issue for more information.

Literal expressions
Escapes
String continuation escapes


The Rust Reference › Literal expressions › Character literal expressions

A character literal expression consists of a single [CHAR_LITERAL] token.
The expression's type is the primitive [`char`] type.
The token must not have a suffix.
The token's _literal content_ is the sequence of characters following the first `U+0027` (`'`) and preceding the last `U+0027` (`'`) in the string representation of the token.
The literal expression's _represented character_ is derived from the literal content as follows:
* If the literal content is one of the following forms of escape sequence, the represented character is the escape sequence's escaped value:
    * [Simple escapes]
    * [7-bit escapes]
    * [Unicode escapes]
* Otherwise the represented character is the single character that makes up the literal content.
The expression's value is the [`char`] corresponding to the represented character's [Unicode scalar value].
The permitted forms of a [CHAR_LITERAL] token ensure that these rules always produce a single character.
Examples of character literal expressions:
```rust
'R';                               // R
'\'';                              // '
'\x52';                            // R
'\u{00E6}';                        // LATIN SMALL LETTER AE (U+00E6)
```

Literal expressions
Character literal expressions


The Rust Reference › Literal expressions › String literal expressions

A string literal expression consists of a single [STRING_LITERAL] or [RAW_STRING_LITERAL] token.
The expression's type is a shared reference (with `static` lifetime) to the primitive [`str`] type. That is, the type is `&'static str`.
The token must not have a suffix.
The token's _literal content_ is the sequence of characters following the first `U+0022` (`"`) and preceding the last `U+0022` (`"`) in the string representation of the token.
The literal expression's _represented string_ is a sequence of characters derived from the literal content as follows:
* If the token is a [STRING_LITERAL], each escape sequence of any of the following forms occurring in the literal content is replaced by the escape sequence's escaped value.
    * [Simple escapes]
    * [7-bit escapes]
    * [Unicode escapes]
    * [String continuation escapes]
  These replacements take place in left-to-right order. For example, the token `"\\x41"` is converted to the characters `\` `x` `4` `1`.
* If the token is a [RAW_STRING_LITERAL], the represented string is identical to the literal content.
The expression's value is a reference to a statically allocated [`str`] containing the UTF-8 encoding of the represented string.
Examples of string literal expressions:
```rust
"foo"; r"foo";                     // foo
"\"foo\""; r#""foo""#;             // "foo"

"foo #\"# bar";
r##"foo #"# bar"##;                // foo #"# bar

"\x52"; "R"; r"R";                 // R
"\\x52"; r"\x52";                  // \x52
```

Literal expressions
String literal expressions


The Rust Reference › Literal expressions › Byte literal expressions

A byte literal expression consists of a single [BYTE_LITERAL] token.
The expression's type is the primitive `u8` type.
The token must not have a suffix.
The token's _literal content_ is the sequence of characters following the first `U+0027` (`'`) and preceding the last `U+0027` (`'`) in the string representation of the token.
The literal expression's _represented character_ is derived from the literal content as follows:
* If the literal content is one of the following forms of escape sequence, the represented character is the escape sequence's escaped value:
    * [Simple escapes]
    * [8-bit escapes]
* Otherwise the represented character is the single character that makes up the literal content.
The expression's value is the represented character's [Unicode scalar value].
The permitted forms of a [BYTE_LITERAL] token ensure that these rules always produce a single character, whose Unicode scalar value is in the range of `u8`.
Examples of byte literal expressions:
```rust
b'R';                              // 82
b'\'';                             // 39
b'\x52';                           // 82
b'\xA0';                           // 160
```

Literal expressions
Byte literal expressions


The Rust Reference › Literal expressions › Byte string literal expressions

A byte string literal expression consists of a single [BYTE_STRING_LITERAL] or [RAW_BYTE_STRING_LITERAL] token.
The expression's type is a shared reference (with `static` lifetime) to an array whose element type is `u8`. That is, the type is `&'static [u8; N]`, where `N` is the number of bytes in the represented string described below.
The token must not have a suffix.
The token's _literal content_ is the sequence of characters following the first `U+0022` (`"`) and preceding the last `U+0022` (`"`) in the string representation of the token.
The literal expression's _represented string_ is a sequence of characters derived from the literal content as follows:
* If the token is a [BYTE_STRING_LITERAL], each escape sequence of any of the following forms occurring in the literal content is replaced by the escape sequence's escaped value.
    * [Simple escapes]
    * [8-bit escapes]
    * [String continuation escapes]
  These replacements take place in left-to-right order. For example, the token `b"\\x41"` is converted to the characters `\` `x` `4` `1`.
* If the token is a [RAW_BYTE_STRING_LITERAL], the represented string is identical to the literal content.
The expression's value is a reference to a statically allocated array containing the [Unicode scalar values] of the characters in the represented string, in the same order.
The permitted forms of [BYTE_STRING_LITERAL] and [RAW_BYTE_STRING_LITERAL] tokens ensure that these rules always produce array element values in the range of `u8`.
Examples of byte string literal expressions:

Literal expressions
Byte string literal expressions


The Rust Reference › Literal expressions › Byte string literal expressions

```rust
b"foo"; br"foo";                     // foo
b"\"foo\""; br#""foo""#;             // "foo"

b"foo #\"# bar";
br##"foo #"# bar"##;                 // foo #"# bar

b"\x52"; b"R"; br"R";                // R
b"\\x52"; br"\x52";                  // \x52
```


The Rust Reference › Literal expressions › C string literal expressions

A C string literal expression consists of a single [C_STRING_LITERAL] or [RAW_C_STRING_LITERAL] token.
The expression's type is a shared reference (with `static` lifetime) to the standard library [CStr] type. That is, the type is `&'static core::ffi::CStr`.
The token must not have a suffix.
The token's _literal content_ is the sequence of characters following the first `"` and preceding the last `"` in the string representation of the token.
The literal expression's _represented bytes_ are a sequence of bytes derived from the literal content as follows:
* If the token is a [C_STRING_LITERAL], the literal content is treated as a sequence of items, each of which is either a single Unicode character other than `\` or an [escape]. The sequence of items is converted to a sequence of bytes as follows:
  * Each single Unicode character contributes its UTF-8 representation.
  * Each [simple escape] contributes the [Unicode scalar value] of its escaped value.
  * Each [8-bit escape] contributes a single byte containing the [Unicode scalar value] of its escaped value.
  * Each [unicode escape] contributes the UTF-8 representation of its escaped value.
  * Each [string continuation escape] contributes no bytes.
* If the token is a [RAW_C_STRING_LITERAL], the represented bytes are the UTF-8 encoding of the literal content.
The permitted forms of [C_STRING_LITERAL] and [RAW_C_STRING_LITERAL] tokens ensure that the represented bytes never include a null byte.
The expression's value is a reference to a statically allocated [CStr] whose array of bytes contains the represented bytes followed by a null byte.
Examples of C string literal expressions:

Literal expressions
C string literal expressions


The Rust Reference › Literal expressions › C string literal expressions

```rust
c"foo"; cr"foo";                     // foo
c"\"foo\""; cr#""foo""#;             // "foo"

c"foo #\"# bar";
cr##"foo #"# bar"##;                 // foo #"# bar

c"\x52"; c"R"; cr"R";                // R
c"\\x52"; cr"\x52";                  // \x52

c"æ";                                // LATIN SMALL LETTER AE (U+00E6)
c"\u{00E6}";                         // LATIN SMALL LETTER AE (U+00E6)
c"\xC3\xA6";                         // LATIN SMALL LETTER AE (U+00E6)

c"\xE6".to_bytes();                  // [230]
c"\u{00E6}".to_bytes();              // [195, 166]
```


The Rust Reference › Literal expressions › Integer literal expressions

An integer literal expression consists of a single [INTEGER_LITERAL] token.
If the token has a [suffix], the suffix must be the name of one of the primitive integer types: `u8`, `i8`, `u16`, `i16`, `u32`, `i32`, `u64`, `i64`, `u128`, `i128`, `usize`, or `isize`, and the expression has that type.
If the token has no suffix, the expression's type is determined by type inference:
* If an integer type can be _uniquely_ determined from the surrounding program context, the expression has that type.
* If the program context under-constrains the type, it defaults to the signed 32-bit integer `i32`.
* If the program context over-constrains the type, it is considered a static type error.
Examples of integer literal expressions:
```rust
123;                               // type i32
123i32;                            // type i32
123u32;                            // type u32
123_u32;                           // type u32
let a: u64 = 123;                  // type u64

0xff;                              // type i32
0xff_u8;                           // type u8

0o70;                              // type i32
0o70_i16;                          // type i16

0b1111_1111_1001_0000;             // type i32
0b1111_1111_1001_0000i64;          // type i64

0usize;                            // type usize
```
The value of the expression is determined from the string representation of the token as follows:

Literal expressions
Integer literal expressions


The Rust Reference › Literal expressions › Integer literal expressions

* An integer radix is chosen by inspecting the first two characters of the string, as follows:
    * `0b` indicates radix 2
    * `0o` indicates radix 8
    * `0x` indicates radix 16
    * otherwise the radix is 10.
* If the radix is not 10, the first two characters are removed from the string.
* Any suffix is removed from the string.
* Any underscores are removed from the string.
* The string is converted to a `u128` value as if by [`u128::from_str_radix`] with the chosen radix. If the value does not fit in `u128`, it is a compiler error.
* The `u128` value is converted to the expression's type via a [numeric cast].
The final cast will truncate the value of the literal if it does not fit in the expression's type. `rustc` includes a [lint check] named `overflowing_literals`, defaulting to `deny`, which rejects expressions where this occurs.
`-1i8`, for example, is an application of the [negation operator] to the literal expression `1i8`, not a single integer literal expression. See [Overflow] for notes on representing the most negative value for a signed type.


The Rust Reference › Literal expressions › Floating-point literal expressions

A floating-point literal expression has one of two forms:
 * a single [FLOAT_LITERAL] token
 * a single [INTEGER_LITERAL] token which has a suffix and no radix indicator
If the token has a [suffix], the suffix must be the name of one of the primitive floating-point types: `f32` or `f64`, and the expression has that type.
If the token has no suffix, the expression's type is determined by type inference:
* If a floating-point type can be _uniquely_ determined from the surrounding program context, the expression has that type.
* If the program context under-constrains the type, it defaults to `f64`.
* If the program context over-constrains the type, it is considered a static type error.
Examples of floating-point literal expressions:
```rust
123.0f64;        // type f64
0.1f64;          // type f64
0.1f32;          // type f32
12E+99_f64;      // type f64
5f32;            // type f32
let x: f64 = 2.; // type f64
```
The value of the expression is determined from the string representation of the token as follows:
* Any suffix is removed from the string.
* Any underscores are removed from the string.
* The string is converted to the expression's type as if by [`f32::from_str`] or [`f64::from_str`].
`-1.0`, for example, is an application of the [negation operator] to the literal expression `1.0`, not a single floating-point literal expression.

Literal expressions
Floating-point literal expressions


The Rust Reference › Literal expressions › Floating-point literal expressions

`inf` and `NaN` are not literal tokens. The [`f32::INFINITY`], [`f64::INFINITY`], [`f32::NAN`], and [`f64::NAN`] constants can be used instead of literal expressions. In `rustc`, a literal large enough to be evaluated as infinite will trigger the `overflowing_literals` lint check.


The Rust Reference › Literal expressions › Boolean literal expressions

A boolean literal expression consists of one of the keywords `true` or `false`.
The expression's type is the primitive [boolean type], and its value is:
 * true if the keyword is `true`
 * false if the keyword is `false`

Literal expressions
Boolean literal expressions


The Rust Reference › Path expressions

```grammar,expressions
PathExpression ->
      PathInExpression
    | QualifiedPathInExpression
```
A [path] used as an expression context denotes either a local variable or an item.
Path expressions that resolve to local or static variables are [place expressions]; other paths are [value expressions].
Using a [`static mut`] variable requires an [`unsafe` block].
```rust
local_var;
globals::STATIC_VAR;
unsafe { globals::STATIC_MUT_VAR };
let some_constructor = Some::<i32>;
let push_integer = Vec::<i32>::push;
let slice_reverse = <[i32]>::reverse;
```
Evaluation of associated constants is handled the same way as [`const` blocks].


The Rust Reference › Block expressions

```grammar,expressions
BlockExpression ->
    `{`
        InnerAttribute*
        Statements?
    `}`

BlockExpressionNoInnerAttributes ->
    `{`
        Statements?
    `}`

Statements ->
      Statement+
    | Statement+ ExpressionWithoutBlock
    | ExpressionWithoutBlock
```
A *block expression*, or *block*, is a control flow expression and anonymous namespace scope for items and variable declarations.
As a control flow expression, a block sequentially executes its component non-item declaration statements and then its final optional expression.
As an anonymous namespace scope, item declarations are only in scope inside the block itself and variables declared by `let` statements are in scope from the next statement until the end of the block. See the [scopes] chapter for more details.
The syntax for a block is `{`, then any [inner attributes], then any number of [statements], then an optional expression, called the final operand, and finally a `}`.
Statements are usually required to be followed by a semicolon, with two exceptions:
1. Item declaration statements do not need to be followed by a semicolon.
2. Expression statements usually require a following semicolon except if its outer expression is a flow control expression.
Furthermore, extra semicolons between statements are allowed, but these semicolons do not affect semantics.
When evaluating a block expression, each statement, except for item declaration statements, is executed sequentially.
Then the final operand is executed, if given.
When a block contains a [final operand], the block has the type and value of that final operand.
```rust
let x: u8 = { 0u8 }; // `0u8` is the final operand.
assert_eq!(x, 0);
let x: u8 = { (); 0u8 }; // As above.
assert_eq!(x, 0);
```
When a block does not contain a [final operand] and the block does not diverge, the block has [unit type] and [unit value].


The Rust Reference › Block expressions

```rust
let x: () = {}; // Has no final operand.
assert_eq!(x, ());
let x: () = { 0u8; }; // As above.
assert_eq!(x, ());
```
When a block does not contain a [final operand] and the block [diverges], the block has the [never type] and has no final value (because its type is [uninhabited]).
```rust,no_run
fn f() -> ! { loop {}; } // Diverges and has no final operand.
//          ^^^^^^^^^^^^
// The body of a function is a block expression.
```
Observe that a block having no final operand is distinct from having an explicit final operand with unit type.  E.g., even though this block diverges, the type of the block is [unit] rather than [never].
```rust,compile_fail,E0308
fn f() -> ! { loop {}; () } // ERROR: Mismatched types.
//          ^^^^^^^^^^^^^^^ This block has unit type.
```
As a control flow expression, if a block expression is the outer expression of an expression statement, the expected type is `()` unless it is followed immediately by a semicolon.
A block is considered to be diverging if all reachable control flow paths contain a diverging expression, unless that expression is a [place expression] that is not read from.


The Rust Reference › Block expressions

```rust,no_run
fn no_control_flow() -> ! {
    // There are no conditional statements, so this entire function body is diverging.
    loop {}
}

fn control_flow_diverging() -> ! {
    // All paths are diverging, so this entire function body is diverging.
    if true {
        loop {}
    } else {
        loop {}
    }
}

fn control_flow_not_diverging() -> () {
    // Some paths are not diverging, so this entire block is not diverging.
    if true {
        ()
    } else {
        loop {}
    }
}

// Note: This makes use of the unstable never type which is only available on
// Rust's nightly channel. This is done for illustration purposes. It is
// possible to encounter this scenario in stable Rust, but requires a more
// convoluted example.
struct Foo {
    x: !,
}

fn make<T>() -> T { loop {} }

fn diverging_place_read() -> ! {
    let foo = Foo { x: make() };
    // A read of a place expression produces a diverging block.
    let _x = foo.x;
}
```
```rust,compile_fail,E0308
fn diverging_place_not_read() -> ! {
    let foo = Foo { x: make() };
    // Assignment to `_` means the place is not read.
    let _ = foo.x;
} // ERROR: Mismatched types.
```
Blocks are always [value expressions] and evaluate the last operand in value expression context.
This can be used to force moving a value if really needed. For example, the following example fails on the call to `consume_self` because the struct was moved out of `s` in the block expression.


The Rust Reference › Block expressions

```rust,compile_fail
struct Struct;

impl Struct {
    fn consume_self(self) {}
    fn borrow_self(&self) {}
}

fn move_by_block_expression() {
    let s = Struct;

    // Move the value out of `s` in the block expression.
    (&{ s }).borrow_self();

    // Fails to execute because `s` is moved out of.
    s.consume_self();
}
```


The Rust Reference › Block expressions › `async` blocks

```grammar,expressions
AsyncBlockExpression -> `async` `move`? BlockExpression
```
An *async block* is a variant of a block expression which evaluates to a future.
The final expression of the block, if present, determines the result value of the future.
Executing an async block is similar to executing a closure expression: its immediate effect is to produce and return an anonymous type.
Whereas closures return a type that implements one or more of the [`std::ops::Fn`] traits, however, the type returned for an async block implements the [`std::future::Future`] trait.
The actual data format for this type is unspecified.
The future type that rustc generates is roughly equivalent to an enum with one variant per `await` point, where each variant stores the data needed to resume from its corresponding point.
[!EDITION-2018]
Async blocks are only available beginning with Rust 2018.


The Rust Reference › Block expressions › `async` blocks › Capture modes

Async blocks capture variables from their environment using the same [capture modes] as closures. Like closures, when written `async { .. }` the capture mode for each variable will be inferred from the content of the block. `async move { .. }` blocks however will move all referenced variables into the resulting future.

Block expressions
`async` blocks
Capture modes


The Rust Reference › Block expressions › `async` blocks › Async context

Because async blocks construct a future, they define an **async context** which can in turn contain [`await` expressions]. Async contexts are established by async blocks as well as the bodies of async functions, whose semantics are defined in terms of async blocks.

Block expressions
`async` blocks
Async context


The Rust Reference › Block expressions › `async` blocks › Control-flow operators

Async blocks act like a function boundary, much like closures.
Therefore, the `?` operator and `return` expressions both affect the output of the future, not the enclosing function or other context. That is, `return <expr>` from within an async block will return the result of `<expr>` as the output of the future. Similarly, if `<expr>?` propagates an error, that error is propagated as the result of the future.
Finally, the `break` and `continue` keywords cannot be used to branch out from an async block. Therefore the following is illegal:
```rust,compile_fail
loop {
    async move {
        break; // error[E0267]: `break` inside of an `async` block
    }
}
```

Block expressions
`async` blocks
Control-flow operators


The Rust Reference › Block expressions › `const` blocks

```grammar,expressions
ConstBlockExpression -> `const` BlockExpression
```
A *const block* is a variant of a block expression whose body evaluates at compile-time instead of at runtime.
Const blocks allows you to define a constant value without having to define new [constant items], and thus they are also sometimes referred as *inline consts*. It also supports type inference so there is no need to specify the type, unlike [constant items].
Const blocks have the ability to reference generic parameters in scope, unlike free constant items. They are desugared to constant items with generic parameters in scope (similar to associated constants, but without a trait or type they are associated with). For example, this code:
```rust
fn foo<T>() -> usize {
    const { std::mem::size_of::<T>() + 1 }
}
```
is equivalent to:
```rust
fn foo<T>() -> usize {
    {
        struct Const<T>(T);
        impl<T> Const<T> {
            const CONST: usize = std::mem::size_of::<T>() + 1;
        }
        Const::<T>::CONST
    }
}
```
If the const block expression is executed at runtime, then the constant is guaranteed to be evaluated, even if its return value is ignored:
```rust
fn foo<T>() -> usize {
    // If this code ever gets executed, then the assertion has definitely
    // been evaluated at compile-time.
    const { assert!(std::mem::size_of::<T>() > 0); }
    // Here we can have unsafe code relying on the type being non-zero-sized.
    /* ... */
    42
}
```
If the const block expression is not executed at runtime, it may or may not be evaluated:
```rust,compile_fail
if false {
    // The panic may or may not occur when the program is built.
    const { panic!(); }
}
```


The Rust Reference › Block expressions › `unsafe` blocks

```grammar,expressions
UnsafeBlockExpression -> `unsafe` BlockExpression
```
_See [`unsafe` blocks] for more information on when to use `unsafe`_.
A block of code can be prefixed with the `unsafe` keyword to permit [unsafe operations]. Examples:
```rust
unsafe {
    let b = [13u8, 17u8];
    let a = &b[0] as *const u8;
    assert_eq!(*a, 13);
    assert_eq!(*a.offset(1), 17);
}

let a = unsafe { an_unsafe_fn() };
```


The Rust Reference › Block expressions › Labeled block expressions

Labeled block expressions are documented in the [Loops and other breakable expressions] section.

Block expressions
Labeled block expressions


The Rust Reference › Block expressions › Attributes on block expressions

[Inner attributes] are allowed directly after the opening brace of a block expression in the following situations:
* [Function] and [method] bodies.
* Loop bodies ([`loop`], [`while`], and [`for`]).
* Block expressions used as a [statement].
* Block expressions as elements of [array expressions], [tuple expressions], [call expressions], and tuple-style [struct] expressions.
* A block expression as the tail expression of another block expression.
The attributes that have meaning on a block expression are [`cfg`] and [the lint check attributes].
For example, this function returns `true` on unix platforms and `false` on other platforms.
```rust
fn is_unix_platform() -> bool {
    #[cfg(unix)] { true }
    #[cfg(not(unix))] { false }
}
```

Block expressions
Attributes on block expressions


The Rust Reference › Operator expressions

```grammar,expressions
OperatorExpression ->
      BorrowExpression
    | DereferenceExpression
    | TryPropagationExpression
    | NegationExpression
    | ArithmeticOrLogicalExpression
    | ComparisonExpression
    | LazyBooleanExpression
    | TypeCastExpression
    | AssignmentExpression
    | CompoundAssignmentExpression
```
Operators are defined for built in types by the Rust language.
Many of the following operators can also be overloaded using traits in `std::ops` or `std::cmp`.


The Rust Reference › Operator expressions › Overflow

Integer operators will panic when they overflow when compiled in debug mode. The `-C debug-assertions` and `-C overflow-checks` compiler flags can be used to control this more directly. The following things are considered to be overflow:
* When `+`, `*` or binary `-` create a value greater than the maximum value, or less than the minimum value that can be stored.
* Applying unary `-` to the most negative value of any signed integer type, unless the operand is a [literal expression] (or a literal expression standing alone inside one or more grouped expressions).
* Using `/` or `%`, where the left-hand argument is the smallest integer of a signed integer type and the right-hand argument is `-1`. These checks occur even when `-C overflow-checks` is disabled, for legacy reasons.
* Using `<<` or `>>` where the right-hand argument is greater than or equal to the number of bits in the type of the left-hand argument, or is negative.
The exception for literal expressions behind unary `-` means that forms such as `-128_i8` or `let j: i8 = -(128)` never cause a panic and have the expected value of -128.
In these cases, the literal expression already has the most negative value for its type (for example, `128_i8` has the value -128) because integer literals are truncated to their type per the description in Integer literal expressions.
Negation of these most negative values leaves the value unchanged due to two's complement overflow conventions.
In `rustc`, these most negative expressions are also ignored by the `overflowing_literals` lint check.


The Rust Reference › Operator expressions › Borrow operators

```grammar,expressions
BorrowExpression ->
      (`&`|`&&`) Expression
    | (`&`|`&&`) `mut` Expression
    | (`&`|`&&`) `raw` `const` Expression
    | (`&`|`&&`) `raw` `mut` Expression
```
The `&` (shared borrow) and `&mut` (mutable borrow) operators are unary prefix operators.
When applied to a [place expression], this expressions produces a reference (pointer) to the location that the value refers to.
The memory location is also placed into a borrowed state for the duration of the reference. For a shared borrow (`&`), this implies that the place may not be mutated, but it may be read or shared again. For a mutable borrow (`&mut`), the place may not be accessed in any way until the borrow expires.
`&mut` evaluates its operand in a mutable place expression context.
If the `&` or `&mut` operators are applied to a [value expression], then a [temporary value] is created.
These operators cannot be overloaded.
```rust
{
    // a temporary with value 7 is created that lasts for this scope.
    let shared_reference = &7;
}
let mut array = [-2, 3, 9];
{
    // Mutably borrows `array` for this scope.
    // `array` may only be used through `mutable_reference`.
    let mutable_reference = &mut array;
}
```
Even though `&&` is a single token (the lazy 'and' operator), when used in the context of borrow expressions it works as two borrows:


The Rust Reference › Operator expressions › Borrow operators

```rust
// same meanings:
let a = &&  10;
let a = & & 10;

// same meanings:
let a = &&&&  mut 10;
let a = && && mut 10;
let a = & & & & mut 10;
```


The Rust Reference › Operator expressions › Borrow operators › Raw borrow operators

`&raw const` and `&raw mut` are the *raw borrow operators*.
The operand expression of these operators is evaluated in place expression context.
`&raw const expr` then creates a const raw pointer of type `*const T` to the given place, and `&raw mut expr` creates a mutable raw pointer of type `*mut T`.
The raw borrow operators must be used instead of a borrow operator whenever the place expression could evaluate to a place that is not properly aligned or does not store a valid value as determined by its type, or whenever creating a reference would introduce incorrect aliasing assumptions. In those situations, using a borrow operator would cause [undefined behavior] by creating an invalid reference, but a raw pointer may still be constructed.
The following is an example of creating a raw pointer to an unaligned place through a `packed` struct:
```rust
#[repr(packed)]
struct Packed {
    f1: u8,
    f2: u16,
}

let packed = Packed { f1: 1, f2: 2 };
// `&packed.f2` would create an unaligned reference, and thus be undefined behavior!
let raw_f2 = &raw const packed.f2;
assert_eq!(unsafe { raw_f2.read_unaligned() }, 2);
```
The following is an example of creating a raw pointer to a place that does not contain a valid value:
```rust
use std::mem::MaybeUninit;

struct Demo {
    field: bool,
}

let mut uninit = MaybeUninit::<Demo>::uninit();
// `&uninit.as_mut().field` would create a reference to an uninitialized `bool`,
// and thus be undefined behavior!
let f1_ptr = unsafe { &raw mut (*uninit.as_mut_ptr()).field };
unsafe { f1_ptr.write(true); }
let init = unsafe { uninit.assume_init() };
```

Operator expressions
Borrow operators
Raw borrow operators


The Rust Reference › Operator expressions › The dereference operator

```grammar,expressions
DereferenceExpression -> `*` Expression
```
The `*` (dereference) operator is also a unary prefix operator.
When applied to a pointer or [`Box`], it denotes the pointed-to location.
If the expression is of type `&mut T`, `*mut T`, or `Box<T>`, and is either a local variable, a (nested) field of a local variable or is a mutable [place expression], then the resulting memory location can be assigned to.
When applied to a [`Box`], the resultant place may be [moved from].
Dereferencing a raw pointer requires `unsafe`.
On non-pointer types `*x` is equivalent to `*std::ops::Deref::deref(&x)` in an immutable place expression context and `*std::ops::DerefMut::deref_mut(&mut x)` in a mutable place expression context, except that when `*x` undergoes [temporary lifetime extension], the dereferenced expression `x` also has its [temporary scope] extended.
```rust
let a = &7;
assert_eq!(*a, 7);
let b = &mut 9;
*b = 11;
assert_eq!(*b, 11);
let c = Box::new(NoCopy);
let d: NoCopy = *c;
```
```rust
// The temporary holding the result of `String::new()` is extended
// to live to the end of the block, so `x` may be used in subsequent
// statements.
let x = &*String::new();
```

Operator expressions
The dereference operator


The Rust Reference › Operator expressions › The dereference operator

```rust,compile_fail,E0716
// The temporary holding the result of `String::new()` is dropped at
// the end of the statement, so it's an error to use `y` after.
let y = &*std::ops::Deref::deref(&String::new()); // ERROR
```


The Rust Reference › Operator expressions › The try propagation expression

```grammar,expressions
TryPropagationExpression -> Expression `?`
```
The try propagation expression uses the value of the inner expression and the [`Try`] trait to decide whether to produce a value, and if so, what value to produce, or whether to return a value to the caller, and if so, what value to return.
```rust
fn try_to_parse() -> Result<i32, ParseIntError> {
    let x: i32 = "123".parse()?; // `x` is `123`.
    let y: i32 = "24a".parse()?; // Returns an `Err()` immediately.
    Ok(x + y)                    // Doesn't run.
}

let res = try_to_parse();
println!("{res:?}");
```
```rust
fn try_option_some() -> Option<u8> {
    let val = Some(1)?;
    Some(val)
}
assert_eq!(try_option_some(), Some(1));

fn try_option_none() -> Option<u8> {
    let val = None?;
    Some(val)
}
assert_eq!(try_option_none(), None);
```
```rust
use std::ops::ControlFlow;

pub struct TreeNode<T> {
    value: T,
    left: Option<Box<TreeNode<T>>>,
    right: Option<Box<TreeNode<T>>>,
}

impl<T> TreeNode<T> {
    pub fn traverse_inorder<B>(&self, f: &mut impl FnMut(&T) -> ControlFlow<B>) -> ControlFlow<B> {
        if let Some(left) = &self.left {
            left.traverse_inorder(f)?;
        }
        f(&self.value)?;
        if let Some(right) = &self.right {
            right.traverse_inorder(f)?;
        }
        ControlFlow::Continue(())
    }
}
```
The [`Try`] trait is currently unstable, and thus cannot be implemented for user types.

Operator expressions
The try propagation expression


The Rust Reference › Operator expressions › The try propagation expression

The try propagation expression is currently roughly equivalent to:
```rust
match core::ops::Try::branch(expr) {
    core::ops::ControlFlow::Continue(val) => val,
    core::ops::ControlFlow::Break(residual) =>
        return core::ops::FromResidual::from_residual(residual),
}
```
The try propagation operator is sometimes called *the question mark operator*, *the `?` operator*, or *the try operator*.
The try propagation operator can be applied to expressions with the type of:


The Rust Reference › Operator expressions › The try propagation expression

- [`Result<T, E>`]
    - `Result::Ok(val)` evaluates to `val`.
    - `Result::Err(e)` returns `Result::Err(From::from(e))`.
- [`Option<T>`]
    - `Option::Some(val)` evaluates to `val`.
    - `Option::None` returns `Option::None`.
- `ControlFlow<B, C>`
    - `ControlFlow::Continue(c)` evaluates to `c`.
    - `ControlFlow::Break(b)` returns `ControlFlow::Break(b)`.
- `Poll<Result<T, E>>`
    - `Poll::Ready(Ok(val))` evaluates to `Poll::Ready(val)`.
    - `Poll::Ready(Err(e))` returns `Poll::Ready(Err(From::from(e)))`.
    - `Poll::Pending` evaluates to `Poll::Pending`.
- `Poll<Option<Result<T, E>>>`
    - `Poll::Ready(Some(Ok(val)))` evaluates to `Poll::Ready(Some(val))`.
    - `Poll::Ready(Some(Err(e)))` returns `Poll::Ready(Some(Err(From::from(e))))`.
    - `Poll::Ready(None)` evaluates to `Poll::Ready(None)`.
    - `Poll::Pending` evaluates to `Poll::Pending`.


The Rust Reference › Operator expressions › Negation operators

```grammar,expressions
NegationExpression ->
      `-` Expression
    | `!` Expression
```
These are the last two unary operators.
This table summarizes the behavior of them on primitive types and which traits are used to overload these operators for other types. Remember that signed integers are always represented using two's complement. The operands of all of these operators are evaluated in value expression context so are moved or copied.
| Symbol | Integer     | `bool`        | Floating Point | Overloading Trait  |
|--------|-------------|-------------- |----------------|--------------------|
| `-`    | Negation*   |               | Negation       | `std::ops::Neg`    |
| `!`    | Bitwise NOT | [Logical NOT] |                | `std::ops::Not`    |
\* Only for signed integer types.
Here are some example of these operators
```rust
let x = 6;
assert_eq!(-x, -6);
assert_eq!(!x, -7);
assert_eq!(true, !false);
```


The Rust Reference › Operator expressions › Arithmetic and logical binary operators

```grammar,expressions
ArithmeticOrLogicalExpression ->
      Expression `+` Expression
    | Expression `-` Expression
    | Expression `*` Expression
    | Expression `/` Expression
    | Expression `%` Expression
    | Expression `&` Expression
    | Expression `|` Expression
    | Expression `^` Expression
    | Expression `<<` Expression
    | Expression `>>` Expression
```
Binary operators expressions are all written with infix notation.
This table summarizes the behavior of arithmetic and logical binary operators on primitive types and which traits are used to overload these operators for other types. Remember that signed integers are always represented using two's complement. The operands of all of these operators are evaluated in value expression context so are moved or copied.

Operator expressions
Arithmetic and logical binary operators


The Rust Reference › Operator expressions › Arithmetic and logical binary operators

| Symbol | Integer                 | `bool`        | Floating Point | Overloading Trait  | Overloading Compound Assignment Trait |
|--------|-------------------------|---------------|----------------|--------------------| ------------------------------------- |
| `+`    | Addition                |               | Addition       | `std::ops::Add`    | `std::ops::AddAssign`                 |
| `-`    | Subtraction             |               | Subtraction    | `std::ops::Sub`    | `std::ops::SubAssign`                 |
| `*`    | Multiplication          |               | Multiplication | `std::ops::Mul`    | `std::ops::MulAssign`                 |
| `/`    | Division*†              |               | Division       | `std::ops::Div`    | `std::ops::DivAssign`                 |
| `%`    | Remainder**†            |               | Remainder      | `std::ops::Rem`    | `std::ops::RemAssign`                 |
| `&`    | Bitwise AND             | [Logical AND] |                | `std::ops::BitAnd` | `std::ops::BitAndAssign`              |
| `\|` | Bitwise OR | [Logical OR]  |                | `std::ops::BitOr`  | `std::ops::BitOrAssign`               |
| `^`    | Bitwise XOR             | [Logical XOR] |                | `std::ops::BitXor` | `std::ops::BitXorAssign`              |
| `<<`   | Left Shift              |               |                | `std::ops::Shl`    | `std::ops::ShlAssign`                 |
| `>>`   | Right Shift***          |               |                | `std::ops::Shr`    |  `std::ops::ShrAssign`                |


The Rust Reference › Operator expressions › Arithmetic and logical binary operators

\* Integer division rounds towards zero.
\*\* Rust uses a remainder defined with truncating division. Given `remainder = dividend % divisor`, the remainder will have the same sign as the dividend.
\*\*\* Arithmetic right shift on signed integer types, logical right shift on unsigned integer types.
† For integer types, division by zero panics.
Here are examples of these operators being used.
```rust
assert_eq!(3 + 6, 9);
assert_eq!(5.5 - 1.25, 4.25);
assert_eq!(-5 * 14, -70);
assert_eq!(14 / 3, 4);
assert_eq!(100 % 7, 2);
assert_eq!(0b1010 & 0b1100, 0b1000);
assert_eq!(0b1010 | 0b1100, 0b1110);
assert_eq!(0b1010 ^ 0b1100, 0b110);
assert_eq!(13 << 3, 104);
assert_eq!(-10 >> 2, -3);
```


The Rust Reference › Operator expressions › Comparison operators

```grammar,expressions
ComparisonExpression ->
      Expression `==` Expression
    | Expression `!=` Expression
    | Expression `>` Expression
    | Expression `<` Expression
    | Expression `>=` Expression
    | Expression `<=` Expression
```
Comparison operators are also defined both for primitive types and many types in the standard library.
Parentheses are required when chaining comparison operators. For example, the expression `a == b == c` is invalid and may be written as `(a == b) == c`.
Unlike arithmetic and logical operators, the traits for overloading these operators are used more generally to show how a type may be compared and will likely be assumed to define actual comparisons by functions that use these traits as bounds. Many functions and macros in the standard library can then use that assumption (although not to ensure safety).
Unlike the arithmetic and logical operators above, these operators implicitly take shared borrows of their operands, evaluating them in place expression context:
```rust
a == b;
// is equivalent to
::std::cmp::PartialEq::eq(&a, &b);
```
This means that the operands don't have to be moved out of.
| Symbol | Meaning                  | Overloading method         |
|--------|--------------------------|----------------------------|
| `==`   | Equal                    | `std::cmp::PartialEq::eq`  |
| `!=`   | Not equal                | `std::cmp::PartialEq::ne`  |
| `>`    | Greater than             | `std::cmp::PartialOrd::gt` |
| `<`    | Less than                | `std::cmp::PartialOrd::lt` |
| `>=`   | Greater than or equal to | `std::cmp::PartialOrd::ge` |
| `<=`   | Less than or equal to    | `std::cmp::PartialOrd::le` |
Here are examples of the comparison operators being used.

Operator expressions
Comparison operators


The Rust Reference › Operator expressions › Comparison operators

```rust
assert!(123 == 123);
assert!(23 != -12);
assert!(12.5 > 12.2);
assert!([1, 2, 3] < [1, 3, 4]);
assert!('A' <= 'B');
assert!("World" >= "Hello");
```


The Rust Reference › Operator expressions › Lazy boolean operators

```grammar,expressions
LazyBooleanExpression ->
      Expression `||` Expression
    | Expression `&&` Expression
```
The operators `||` and `&&` may be applied to operands of boolean type. The `||` operator denotes logical 'or', and the `&&` operator denotes logical 'and'.
They differ from `|` and `&` in that the right-hand operand is only evaluated when the left-hand operand does not already determine the result of the expression. That is, `||` only evaluates its right-hand operand when the left-hand operand evaluates to `false`, and `&&` only when it evaluates to `true`.
```rust
let x = false || true; // true
let y = false && panic!(); // false, doesn't evaluate `panic!()`
```

Operator expressions
Lazy boolean operators


The Rust Reference › Operator expressions › Type cast expressions

```grammar,expressions
TypeCastExpression -> Expression `as` TypeNoBounds
```
A type cast expression is denoted with the binary operator `as`.
Executing an `as` expression casts the value on the left-hand side to the type on the right-hand side.
An example of an `as` expression:
```rust
fn average(values: &[f64]) -> f64 {
    let sum: f64 = sum(values);
    let size: f64 = len(values) as f64;
    sum / size
}
```
`as` can be used to explicitly perform coercions, as well as the following additional casts. Any cast that does not fit either a coercion rule or an entry in the table is a compiler error. Here `*T` means either `*const T` or `*mut T`. `m` stands for optional `mut` in reference types and `mut` or `const` in pointer types.

Operator expressions
Type cast expressions


The Rust Reference › Operator expressions › Type cast expressions

| Type of `e`           | `U`                   | Cast performed by `e as U`                            |
|-----------------------|-----------------------|-------------------------------------------------------|
| Integer or Float type | Integer or Float type | Numeric cast                       |
| Enumeration           | Integer type          | Enum cast                             |
| `bool` or `char`      | Integer type          | Primitive to integer cast |
| `u8`                  | `char`                | `u8` to `char` cast             |
| `*T`                  | `*V` (when compatible) | Pointer to pointer cast |
| `*T` where `T: Sized` | Integer type          | Pointer to address cast     |
| Integer type          | `*V` where `V: Sized` | Address to pointer cast     |
| `&m₁ [T; n]`          | `*m₂ T` [^lessmut]    | Array to pointer cast                                 |
| `*m₁ [T; n]`          | `*m₂ T` [^lessmut]    | Array to pointer cast                                 |
| [Function item]       | [Function pointer]    | Function item to function pointer cast                |
| [Function item]       | `*V` where `V: Sized` | Function item to pointer cast                         |
| [Function item]       | Integer               | Function item to address cast                         |
| [Function pointer]    | `*V` where `V: Sized` | Function pointer to pointer cast                      |
| [Function pointer]    | Integer               | Function pointer to address cast                      |
| Closure [^no-capture] | Function pointer      | Closure to function pointer cast                      |


The Rust Reference › Operator expressions › Type cast expressions

[^lessmut]: Only when `m₁` is `mut` or `m₂` is `const`. Casting `mut` reference/pointer to `const` pointer is allowed.
[^no-capture]: Only closures that do not capture (close over) any local variables can be cast to function pointers.


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Numeric cast

* Casting between two integers of the same size (e.g. i32 -> u32) is a no-op (Rust uses 2's complement for negative values of fixed integers)
```rust
  assert_eq!(42i8 as u8, 42u8);
  assert_eq!(-1i8 as u8, 255u8);
  assert_eq!(255u8 as i8, -1i8);
  assert_eq!(-1i16 as u16, 65535u16);
```
* Casting from a larger integer to a smaller integer (e.g. u32 -> u8) will truncate
```rust
  assert_eq!(42u16 as u8, 42u8);
  assert_eq!(1234u16 as u8, 210u8);
  assert_eq!(0xabcdu16 as u8, 0xcdu8);

  assert_eq!(-42i16 as i8, -42i8);
  assert_eq!(1234u16 as i8, -46i8);
  assert_eq!(0xabcdi32 as i8, -51i8);
```
* Casting from a smaller integer to a larger integer (e.g. u8 -> u32) will
    * zero-extend if the source is unsigned
    * sign-extend if the source is signed

Operator expressions
Type cast expressions
Semantics
Numeric cast


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Numeric cast

```rust
  assert_eq!(42i8 as i16, 42i16);
  assert_eq!(-17i8 as i16, -17i16);
  assert_eq!(0b1000_1010u8 as u16, 0b0000_0000_1000_1010u16, "Zero-extend");
  assert_eq!(0b0000_1010i8 as i16, 0b0000_0000_0000_1010i16, "Sign-extend 0");
  assert_eq!(0b1000_1010u8 as i8 as i16, 0b1111_1111_1000_1010u16 as i16, "Sign-extend 1");
```
* Casting from a float to an integer will round the float towards zero
    * `NaN` will return `0`
    * Values larger than the maximum integer value, including `INFINITY`, will saturate to the maximum value of the integer type.
    * Values smaller than the minimum integer value, including `NEG_INFINITY`, will saturate to the minimum value of the integer type.


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Numeric cast

```rust
  assert_eq!(42.9f32 as i32, 42);
  assert_eq!(-42.9f32 as i32, -42);
  assert_eq!(42_000_000f32 as i32, 42_000_000);
  assert_eq!(std::f32::NAN as i32, 0);
  assert_eq!(1_000_000_000_000_000f32 as i32, 0x7fffffffi32);
  assert_eq!(std::f32::NEG_INFINITY as i32, -0x80000000i32);
```
* Casting from an integer to float will produce the closest possible float \*
    * if necessary, rounding is according to `roundTiesToEven` mode \*\*\*
    * on overflow, infinity (of the same sign as the input) is produced
    * note: with the current set of numeric types, overflow can only happen on `u128 as f32` for values greater or equal to `f32::MAX + (0.5 ULP)`
```rust
  assert_eq!(1337i32 as f32, 1337f32);
  assert_eq!(123_456_789i32 as f32, 123_456_790f32, "Rounded");
  assert_eq!(0xffffffff_ffffffff_ffffffff_ffffffff_u128 as f32, std::f32::INFINITY);
```
* Casting from an f32 to an f64 is perfect and lossless


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Enum cast

```rust
  assert_eq!(1_234.5f32 as f64, 1_234.5f64);
  assert_eq!(std::f32::INFINITY as f64, std::f64::INFINITY);
  assert!((std::f32::NAN as f64).is_nan());
```
* Casting from an f64 to an f32 will produce the closest possible f32 \*\*
    * if necessary, rounding is according to `roundTiesToEven` mode \*\*\*
    * on overflow, infinity (of the same sign as the input) is produced
```rust
  assert_eq!(1_234.5f64 as f32, 1_234.5f32);
  assert_eq!(1_234_567_891.123f64 as f32, 1_234_567_890f32, "Rounded");
  assert_eq!(std::f64::INFINITY as f32, std::f32::INFINITY);
  assert!((std::f64::NAN as f32).is_nan());
```
\* if integer-to-float casts with this rounding mode and overflow behavior are not supported natively by the hardware, these casts will likely be slower than expected.
\*\* if f64-to-f32 casts with this rounding mode and overflow behavior are not supported natively by the hardware, these casts will likely be slower than expected.
\*\*\* as defined in IEEE 754-2008 §4.3.1: pick the nearest floating point number, preferring the one with an even least significant digit if exactly halfway between two floating point numbers.

Operator expressions
Type cast expressions
Semantics
Enum cast


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Address to pointer cast

Casts an enum to its discriminant, then uses a numeric cast if needed. Casting is limited to the following kinds of enumerations:
* [Unit-only enums]
* [Field-less enums] without [explicit discriminants], or where only unit-variants have explicit discriminants
```rust
enum Enum { A, B, C }
assert_eq!(Enum::A as i32, 0);
assert_eq!(Enum::B as i32, 1);
assert_eq!(Enum::C as i32, 2);
```
Casting is not allowed if the enum implements [`Drop`].
* `false` casts to `0`, `true` casts to `1`
* `char` casts to the value of the code point, then uses a numeric cast if needed.
```rust
assert_eq!(false as i32, 0);
assert_eq!(true as i32, 1);
assert_eq!('A' as i32, 65);
assert_eq!('Ö' as i32, 214);
```
Casts to the `char` with the corresponding code point.
```rust
assert_eq!(65u8 as char, 'A');
assert_eq!(214u8 as char, 'Ö');
```
Casting from a raw pointer to an integer produces the machine address of the referenced memory. If the integer type is smaller than the pointer type, the address may be truncated; using `usize` avoids this.
Casting from an integer to a raw pointer interprets the integer as a memory address and produces a pointer referencing that memory.
This interacts with the Rust memory model, which is still under development.
A pointer obtained from this cast may suffer additional restrictions even if it is bitwise equal to a valid pointer.
Dereferencing such a pointer may be [undefined behavior] if aliasing rules are not followed.
A trivial example of sound address arithmetic:

Operator expressions
Type cast expressions
Semantics
Address to pointer cast


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Pointer-to-pointer cast

```rust
let mut values: [i32; 2] = [1, 2];
let p1: *mut i32 = values.as_mut_ptr();
let first_address = p1 as usize;
let second_address = first_address + 4; // 4 == size_of::<i32>()
let p2 = second_address as *mut i32;
unsafe {
    *p2 += 1;
}
assert_eq!(values[1], 3);
```
`*const T` / `*mut T` can be cast to `*const U` / `*mut U` with the following behavior:
- If `T` and `U` are both sized, the pointer is returned unchanged.
```rust
let x: i32 = 42;
let p1: *const i32 = &x;
let p2: *const u8 = p1 as *const u8;
// The pointer address remains the same.
assert_eq!(p1 as usize, p2 as usize);
```
- If `T` is unsized and `U` is sized, the cast discards all [metadata] that completes the wide pointer `T` and produces a thin pointer `U` consisting of the data part of the unsized pointer.
```rust
let slice: &[i32] = &[1, 2, 3];
let ptr: *const [i32] = slice as *const [i32];
// Cast from wide pointer (*const [i32]) to thin pointer (*const i32)
// discarding the length metadata.
let data_ptr: *const i32 = ptr as *const i32;
assert_eq!(unsafe { *data_ptr }, 1);
```

Operator expressions
Type cast expressions
Semantics
Pointer-to-pointer cast


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Pointer-to-pointer cast

- If `T` and `U` are both unsized, the pointer is also returned unchanged. In particular, the metadata is preserved exactly. The cast can only be performed if the metadata is compatible according to the below rules:
- When `T` and `U` are unsized with slice metadata, they are always compatible. The metadata of a slice is the number of elements, so casting `*[u16] -> *[u8]` is legal but will result in reducing the number of bytes by half.
```rust
let slice: &[u16] = &[1, 2, 3];
let ptr: *const [u16] = slice as *const [u16];
let byte_ptr: *const [u8] = ptr as *const [u8];
assert_eq!(byte_ptr.len(), 3);
```
- When `T` and `U` are unsized with trait object metadata, the metadata is compatible only when all of the following holds:
  1. The principal trait must be the same.
```rust,compile_fail,E0606
trait Foo {}
trait Bar {}
impl Foo for i32 {}
impl Bar for i32 {}

let x: i32 = 42;
let ptr_foo: *const dyn Foo = &x as *const dyn Foo;
// You can't cast to a different principal trait.
let ptr_bar: *const dyn Bar = ptr_foo as *const dyn Bar; // ERROR
```
  2. Auto traits may be removed.
```rust
trait Foo {}
struct S;
impl Foo for S {}
unsafe impl Send for S {}

let s = S;
let ptr_send: *const (dyn Foo + Send) = &s;
// Removing an auto trait.
let ptr_no_send: *const dyn Foo = ptr_send as *const dyn Foo;
```


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Pointer-to-pointer cast

3. Auto traits may be added only if they are a super trait of the principal trait.
```rust
trait Foo: Send {}
struct S;
impl Foo for S {}
unsafe impl Send for S {}

let s = S;
let ptr_no_send: *const dyn Foo = &s;
// Adding an auto trait.
let ptr_send: *const (dyn Foo + Send) = ptr_no_send as *const (dyn Foo + Send);
```
```rust,compile_fail,E0804
trait Foo {}
// Same as above, except trait Foo does not have Send as a super trait.
let ptr_send: *const (dyn Foo + Send) = ptr_no_send as *const (dyn Foo + Send); // ERROR
```
  4. Trailing lifetimes may only be shortened.
```rust
trait Foo {}

fn shorten_lifetime<'long: 'short, 'short>(
    ptr: *const (dyn Foo + 'long),
) -> *const (dyn Foo + 'short) {
    // Shortening the lifetime is allowed.
    ptr as *const (dyn Foo + 'short)
}
```
```rust,compile_fail
trait Foo {}

fn lengthen_lifetime<'long: 'short, 'short>(
    ptr: *const (dyn Foo + 'short),
) -> *const (dyn Foo + 'long) {
    // It is not allowed to cast to a longer lifetime.
    ptr as *const (dyn Foo + 'long) // ERROR
}
```
  5. Generics (including lifetimes) and associated types must match exactly.


The Rust Reference › Operator expressions › Type cast expressions › Semantics › Pointer-to-pointer cast

```rust,compile_fail,E0606
trait Generic<T> {}
impl Generic<i32> for () {}
impl Generic<u32> for () {}

let x = ();
let ptr_i32: *const dyn Generic<i32> = &x;
// You can't cast to a different generic parameter.
let ptr_u32: *const dyn Generic<u32> = ptr_i32 as *const dyn Generic<u32>; // ERROR
```
```rust
trait HasType {
    type Output;
}

trait Generic<'x, T> {}

fn cast_via_associated<'a, 'b, A, B>(
    ptr: *const dyn Generic<'a, A::Output>,
) -> *const dyn Generic<'b, B::Output>
where
    'a: 'b,
    'b: 'a,
    A: HasType,
    B: HasType<Output = A::Output>, // Forces equality
{
    ptr as *const dyn Generic<'b, B::Output>
}
```
- When `T` or `U` is a struct or tuple type whose last field is unsized, it has the same metadata and compatibility rules as its last field.
```rust
struct Wrapper(u32, [u8]);

let slice: &[u8] = &[1, 2, 3];
let ptr: *const [u8] = slice;

// The metadata (length 3) is preserved when casting to a struct
// where the last field is the unsized type `[u8]`.
let wrapper_ptr: *const Wrapper = ptr as *const Wrapper;

// And preserved when casting back.
let ptr_back: *const [u8] = wrapper_ptr as *const [u8];
assert_eq!(ptr_back.len(), 3);
```


The Rust Reference › Operator expressions › Assignment expressions

```grammar,expressions
AssignmentExpression -> Expression `=` Expression
```
An *assignment expression* moves a value into a specified place.
An assignment expression consists of a [mutable] [assignee expression], the *assignee operand*, followed by an equals sign (`=`) and a [value expression], the *assigned value operand*.
In its most basic form, an assignee expression is a [place expression], and we discuss this case first.
The more general case of destructuring assignment is discussed below, but this case always decomposes into sequential assignments to place expressions, which may be considered the more fundamental case.

Operator expressions
Assignment expressions


The Rust Reference › Operator expressions › Assignment expressions › Basic assignments

Evaluating assignment expressions begins by evaluating its operands. The assigned value operand is evaluated first, followed by the assignee expression.
For destructuring assignment, subexpressions of the assignee expression are evaluated left-to-right.
This is different than other expressions in that the right operand is evaluated before the left one.
It then has the effect of first [dropping] the value at the assigned place, unless the place is an uninitialized local variable or an uninitialized field of a local variable.
Next it either [copies or moves] the assigned value to the assigned place.
An assignment expression always produces the unit value.
Example:
```rust
let mut x = 0;
let y = 0;
x = y;
```

Operator expressions
Assignment expressions
Basic assignments


The Rust Reference › Operator expressions › Assignment expressions › Destructuring assignments

Destructuring assignment is a counterpart to destructuring pattern matches for variable declaration, permitting assignment to complex values, such as tuples or structs. For instance, we may swap two mutable variables:
```rust
let (mut a, mut b) = (0, 1);
// Swap `a` and `b` using destructuring assignment.
(b, a) = (a, b);
```
In contrast to destructuring declarations using `let`, patterns may not appear on the left-hand side of an assignment due to syntactic ambiguities. Instead, a group of expressions that correspond to patterns are designated to be assignee expressions, and permitted on the left-hand side of an assignment. Assignee expressions are then desugared to pattern matches followed by sequential assignment.
The desugared patterns must be irrefutable: in particular, this means that only slice patterns whose length is known at compile-time, and the trivial slice `[..]`, are permitted for destructuring assignment.
The desugaring method is straightforward, and is illustrated best by example.
```rust
(a, b) = (3, 4);

[a, b] = [3, 4];

Struct { x: a, y: b } = Struct { x: 3, y: 4};

// desugars to:

{
    let (_a, _b) = (3, 4);
    a = _a;
    b = _b;
}

{
    let [_a, _b] = [3, 4];
    a = _a;
    b = _b;
}

{
    let Struct { x: _a, y: _b } = Struct { x: 3, y: 4};
    a = _a;
    b = _b;
}
```
Identifiers are not forbidden from being used multiple times in a single assignee expression.

Operator expressions
Assignment expressions
Destructuring assignments


The Rust Reference › Operator expressions › Assignment expressions › Destructuring assignments

[Underscore expressions] and empty [range expressions] may be used to ignore certain values, without binding them.
Note that default binding modes do not apply for the desugared expression.
The desugaring restricts the [temporary scope] of the assigned value operand (the RHS) of a destructuring assignment.
In a basic assignment, the [temporary] is dropped at the end of the enclosing temporary scope. Below, that's the statement. Therefore, the assignment and use is allowed.
```rust
fn f<T>(x: T) -> T { x }
let x;
(x = f(&temp()), x); // OK
```
Conversely, in a destructuring assignment, the temporary is dropped at the end of the `let` statement in the desugaring. As that happens before we try to assign to `x`, below, it fails.
```rust,compile_fail,E0716
[x] = [f(&temp())]; // ERROR
```
This desugars to:
```rust,compile_fail,E0716
{
    let [_x] = [f(&temp())];
    //                     ^
    //      The temporary is dropped here.
    x = _x; // ERROR
}
```
Due to the desugaring, the assigned value operand (the RHS) of a destructuring assignment is an [extending expression] within a newly-introduced block.
Below, because the [temporary scope] is extended to the end of this introduced block, the assignment is allowed.
```rust
[x] = [&temp()]; // OK
```
This desugars to:
```rust
{ let [_x] = [&temp()]; x = _x; } // OK
```
However, if we try to use `x`, even within the same statement, we'll get an error because the [temporary] is dropped at the end of this introduced block.


The Rust Reference › Operator expressions › Assignment expressions › Destructuring assignments

```rust,compile_fail,E0716
([x] = [&temp()], x); // ERROR
```
This desugars to:
```rust,compile_fail,E0716
(
    {
        let [_x] = [&temp()];
        x = _x;
    }, // <-- The temporary is dropped here.
    x, // ERROR
);
```


The Rust Reference › Operator expressions › Compound assignment expressions

```grammar,expressions
CompoundAssignmentExpression ->
      Expression `+=` Expression
    | Expression `-=` Expression
    | Expression `*=` Expression
    | Expression `/=` Expression
    | Expression `%=` Expression
    | Expression `&=` Expression
    | Expression `|=` Expression
    | Expression `^=` Expression
    | Expression `<<=` Expression
    | Expression `>>=` Expression
```
*Compound assignment expressions* combine arithmetic and logical binary operators with assignment expressions.
For example:
```rust
let mut x = 5;
x += 1;
assert!(x == 6);
```
The syntax of compound assignment is a [mutable] [place expression], the *assigned operand*, then one of the operators followed by an `=` as a single token (no whitespace), and then a [value expression], the *modifying operand*.
Unlike other place operands, the assigned place operand must be a place expression.
Attempting to use a value expression is a compiler error rather than promoting it to a temporary.
Evaluation of compound assignment expressions depends on the types of the operands.
If the types of both operands are known, prior to monomorphization, to be primitive, the right hand side is evaluated first, the left hand side is evaluated next, and the place given by the evaluation of the left hand side is mutated by applying the operator to the values of both sides.

Operator expressions
Compound assignment expressions


The Rust Reference › Operator expressions › Compound assignment expressions

```rust
trait Equate {}
impl<T> Equate for (T, T) {}

fn f1(x: (u8,)) {
    let mut order = vec![];
    // The RHS is evaluated first as both operands are of primitive
    // type.
    { order.push(2); x }.0 += { order.push(1); x }.0;
    assert!(order.is_sorted());
}

fn f2(x: (Wrapping<u8>,)) {
    let mut order = vec![];
    // The LHS is evaluated first as `Wrapping<_>` is not a primitive
    // type.
    { order.push(1); x }.0 += { order.push(2); (0u8,) }.0;
    assert!(order.is_sorted());
}

fn f3<T: AddAssign<u8> + Copy>(x: (T,)) where (T, u8): Equate {
    let mut order = vec![];
    // The LHS is evaluated first as one of the operands is a generic
    // parameter, even though that generic parameter can be unified
    // with a primitive type due to the where clause bound.
    { order.push(1); x }.0 += { order.push(2); (0u8,) }.0;
    assert!(order.is_sorted());
}

fn main() {
    f1((0u8,));
    f2((Wrapping(0u8),));
    // We supply a primitive type as the generic argument, but this
    // does not affect the evaluation order in `f3` when
    // monomorphized.
    f3::<u8>((0u8,));
}
```
This is unusual. Elsewhere left to right evaluation is the norm.
See the [eval order test] for more examples.


The Rust Reference › Operator expressions › Compound assignment expressions

Otherwise, this expression is syntactic sugar for using the corresponding trait for the operator (see [expr.arith-logic.behavior]) and calling its method with the left hand side as the [receiver] and the right hand side as the next argument.
For example, the following two statements are equivalent:
```rust
fn f<T: AddAssign + Copy>(mut x: T, y: T) {
    x += y; // Statement 1.
    x.add_assign(y); // Statement 2.
}
```
Surprisingly, desugaring this further to a fully qualified method call is not equivalent, as there is special borrow checker behavior when the mutable reference to the first operand is taken via [autoref].
```rust
fn f<T: AddAssign + Copy>(mut x: T) {
    // Here we used `x` as both the LHS and the RHS. Because the
    // mutable borrow of the LHS needed to call the trait method
    // is taken implicitly by autoref, this is OK.
    x += x; //~ OK
    x.add_assign(x); //~ OK
}
```
```rust,compile_fail,E0503
fn f<T: AddAssign + Copy>(mut x: T) {
    // We can't desugar the above to the below, as once we take the
    // mutable borrow of `x` to pass the first argument, we can't
    // pass `x` by value in the second argument because the mutable
    // reference is still live.
    <T as AddAssign>::add_assign(&mut x, x);
    //~^ ERROR cannot use `x` because it was mutably borrowed
}
```
```rust,compile_fail,E0503
fn f<T: AddAssign + Copy>(mut x: T) {
    // As above.
    (&mut x).add_assign(x);
    //~^ ERROR cannot use `x` because it was mutably borrowed
}
```


The Rust Reference › Operator expressions › Compound assignment expressions

As with normal assignment expressions, compound assignment expressions always produce the unit value.
Avoid writing code that depends on the evaluation order of operands in compound assignments as it can be unusual and surprising.


The Rust Reference › Grouped expressions

```grammar,expressions
GroupedExpression -> `(` Expression `)`
```
A *parenthesized expression* wraps a single expression, evaluating to that expression. The syntax for a parenthesized expression is a `(`, then an expression, called the *enclosed operand*, and then a `)`.
Parenthesized expressions evaluate to the value of the enclosed operand.
A parenthesized expression is a place expression if the enclosed operand is a place expression, and is a value expression if the enclosed operand is a value expression.
Parentheses can be used to explicitly modify the precedence order of subexpressions within an expression.
An example of a parenthesized expression:
```rust
let x: i32 = 2 + 3 * 4; // not parenthesized
let y: i32 = (2 + 3) * 4; // parenthesized
assert_eq!(x, 14);
assert_eq!(y, 20);
```
An example of a necessary use of parentheses is when calling a function pointer that is a member of a struct:
```rust
assert_eq!( a.f (), "The method f");
assert_eq!((a.f)(), "The field f");
```


The Rust Reference › Array and array index expressions › Array expressions

```grammar,expressions
ArrayExpression -> `[` ArrayElements? `]`

ArrayElements ->
      Expression ( `,` Expression )* `,`?
    | Expression `;` Expression
```
*Array expressions* construct arrays. Array expressions come in two forms.
The first form lists out every value in the array.
The syntax for this form is a comma-separated list of expressions of uniform type enclosed in square brackets.
This produces an array containing each of these values in the order they are written.
The syntax for the second form is two expressions separated by a semicolon (`;`) enclosed in square brackets.
The expression before the `;` is called the *repeat operand*.
The expression after the `;` is called the *length operand*.
The length operand must either be an [inferred const] or be a [constant expression] of type `usize` (e.g. a [literal] or a [constant item]).
```rust
const C: usize = 1;
let _: [u8; C] = [0; 1]; // Literal.
let _: [u8; C] = [0; C]; // Constant item.
let _: [u8; C] = [0; _]; // Inferred const.
let _: [u8; C] = [0; (((_)))]; // Inferred const.
```
In an array expression, an [inferred const] is parsed as an expression but then semantically treated as a separate kind of [const generic argument].
An array expression of this form creates an array with the length of the value of the length operand with each element being a copy of the repeat operand. That is, `[a; b]` creates an array containing `b` copies of the value of `a`.

Array and array index expressions
Array expressions


The Rust Reference › Array and array index expressions › Array expressions

If the length operand has a value greater than 1 then this requires the repeat operand to have a type that implements [`Copy`], to be a [const block expression], or to be a [path] to a constant item.
When the repeat operand is a const block or a path to a constant item, it is evaluated the number of times specified in the length operand.
If that value is `0`, then the const block or constant item is not evaluated at all.
For expressions that are neither a const block nor a path to a constant item, it is evaluated exactly once, and then the result is copied the length operand's value times.
```rust
[1, 2, 3, 4];
["a", "b", "c", "d"];
[0; 128];              // array with 128 zeros
[0u8, 0u8, 0u8, 0u8,];
[[1, 0, 0], [0, 1, 0], [0, 0, 1]]; // 2D array
const EMPTY: Vec<i32> = Vec::new();
[EMPTY; 2];
```