I do not expect the following code to work, but as part of grammar exploration, I tried in playground:
fn main() {
struct EOF {};
let lines = vec![Ok("line 1"), Ok("line 2"), Err(EOF {})];
for Ok(line) in lines {
println!("{}", line);
}
}
The error message is
error[E0005]: refutable pattern in `for` loop binding: `Err(_)` not covered
--> src/main.rs:4:9
|
4 | for Ok(line) in lines {
| ^^^^^^^^ pattern `Err(_)` not covered
According to the message above it looks like I only need to add a match arm for the Err
case. But what is the right grammar to do so?
Yes, you can use patterns in many places, but not all of them allow you to conditionally branch when there are multiple possible patterns.
A
for
loop is one place where you cannot add conditions. That's what the error is telling you with "refutable pattern": there's a pattern that will not be handled. Instead, you mostly use the pattern to perform destructuring of the loop variable:Conditional:
match
if let
while let
Unconditional:
for
let
This gets the result you want:
Note that you can use
flat_map
here becauseResult
implements theinto_iter
method provided by theIntoIterator
trait.This is another option using
if let
:You may also want to stop iteration on an
Err
case:You can use patterns as the binding in a
for
loop, but not refutable patterns. The difference between refutable and irrefutable patterns is described here, but the gist of it is, if a pattern could fail, you can't use it in alet
statement or afor
loop. If a pattern can't fail, you can't (currently) use it inif let
orwhile let
. (This last may be changed in a future version to issue a warning instead of failing.)An example of an irrefutable pattern being used in a
for
loop might be something like this:(name, number)
is an irrefutable pattern, because any place where it type checks, it will match. It type checks here because the items being iterated over (defined by the implementation ofIntoIterator
for&HashMap
) are tuples. You could also write the above asbecause
let
is another place where only irrefutable patterns are allowed.