E0017

E0017#

Warning name: ambiguous_loop_argument

The usage of identifier is ambiguous. If it refers to the loop variable, please use as <id> to bind it in the pattern. If it refers to the original value of the variable before entering the loop, please bind it to a new binder outside the loop.

Erroneous example#

///|
fn main {
  let a : StringView = "asdf"
  loop a {
    [_, .. d] => {
      println(a)
      //      ^
      // Warning: The usage of 'a' is ambiguous. If it refers to the loop
      // variable, please use `as a` to bind it in the pattern. If it refers to
      // the original value of 'a' before entering the loop, please bind it to a
      // new binder outside the loop.
      continue d
    }
    [] => ()
  }
}

Output:

asdf
asdf
asdf
asdf

Because a refers to the value of a before entering the loop, therefore the value is always the same.

Suggestion#

Since loop syntax will be removed soon, prefer rewriting new code with a for loop when possible. For example, this code can be written as:

let text : StringView = "asdf"
for i = 0; i < text.length(); i = i + 1 {
  println(text[i:])
}

If you are maintaining existing loop code, and you want to refer to the loop variable that changes with loop iterations, use as <id> to bind it in the pattern.

///|
fn main {
  let a : StringView = "asdf"
  loop a {
    [_, .. d] as a => {
      println(a)
      continue d
    }
    [] => ()
  }
}

Output:

asdf
sdf
df
f

Or, if you want to refer to the original value of the variable before entering the loop, explicitly bind it to another name outside the loop.

///|
fn main {
  let a : StringView = "asdf"
  let b = a
  loop a {
    [_, .. d] => {
      println(b)
      continue d
    }
    [] => ()
  }
}

Output:

asdf
asdf
asdf
asdf