@@ -521,8 +521,11 @@ self.pre_comment.as_ref().map_or(
521521
522522## Control flow expressions
523523
524- This section covers ` if ` , ` if let ` , ` loop ` , ` while ` , ` while let ` , and ` for `
525- expressions.
524+ This section covers ` for ` and ` loop ` expressions, as well as ` if ` and ` while `
525+ expressions with their sub-expression variants. This includes those with a
526+ single ` let ` sub-expression (i.e. ` if let ` and ` while let ` )
527+ as well as "let-chains": those with one or more ` let ` sub-expressions and
528+ one or more bool-type conditions (i.e. ` if a && let Some(b) = c ` ).
526529
527530Put the keyword, any initial clauses, and the opening brace of the block all on
528531a single line, if they fit. Apply the usual rules for [ block
@@ -548,10 +551,11 @@ if let ... {
548551}
549552```
550553
551- If the control line needs to be broken, prefer to break before the ` = ` in `*
552- let` expressions and before ` in` in a ` for` expression; block-indent the
553- following line. If the control line is broken for any reason, put the opening
554- brace on its own line, not indented. Examples:
554+ If the control line needs to be broken, then prefer breaking after the ` = ` for any
555+ ` let ` sub-expression in an ` if ` or ` while ` expression that does not fit,
556+ and before ` in ` in a ` for ` expression; the following line should be block indented.
557+ If the control line is broken for any reason, then the opening brace should be on its
558+ own line and not indented. Examples:
555559
556560``` rust
557561while let Some (foo )
@@ -572,6 +576,68 @@ if a_long_expression
572576{
573577 ...
574578}
579+
580+ if let Some (a ) = b
581+ && another_long_expression
582+ && a_third_long_expression
583+ {
584+ // ...
585+ }
586+
587+ if let Some (relatively_long_thing )
588+ = a_long_expression
589+ && another_long_expression
590+ && a_third_long_expression
591+ {
592+ // ...
593+ }
594+
595+ if some_expr
596+ && another_long_expression
597+ && let Some (relatively_long_thing ) =
598+ a_long_long_long_long_long_long_really_reallllllllllyyyyyyy_long_expression
599+ && a_third_long_expression
600+ {
601+ // ...
602+ }
603+ ```
604+
605+ A let-chain control line is allowed to be formatted on a single line provided
606+ it only consists of two clauses, with the first, left-hand side operand being a literal or an
607+ ` ident ` (which can optionally be preceded by any number of unary prefix operators),
608+ and the second, right-hand side operand being a single-line ` let ` clause. Otherwise,
609+ the control line must be broken and formatted according to the above rules. For example:
610+
611+ ``` rust
612+ if a && let Some (b ) = foo () {
613+ // ...
614+ }
615+
616+ if true && let Some (b ) = foo () {
617+ // ...
618+ }
619+
620+ let operator = if ! from_hir_call && let Some (p ) = parent {
621+ // ...
622+ };
623+
624+ if let Some (b ) = foo ()
625+ && a
626+ {
627+ // ..
628+ }
629+
630+ if foo ()
631+ && let Some (b ) = bar
632+ {
633+ // ...
634+ }
635+
636+ if gen_pos != GenericArgPosition :: Type
637+ && let Some (b ) = gen_args . bindings. first ()
638+ {
639+ // ..
640+ }
575641```
576642
577643Where the initial clause spans multiple lines and ends with one or more closing
0 commit comments