在字符串字符 for 循环中使用可变或不可变引用

lry*_*lry 2 rust

我很困惑可变引用如何在 for 循环中工作,而不可变引用则不然。它是一个迭代器吗?

我发现循环之后,引用chars引用了 value ""

无参考

fn main() {
    let str_value: String = "abc".to_string();

    let chars = str_value.chars();
    for char_value in chars {
        println!("char: {}", char_value);
    }
}
Run Code Online (Sandbox Code Playgroud)
char: a
char: b
char: c
Run Code Online (Sandbox Code Playgroud)

不可变的引用

fn main() {
    let str_value: String = "abc".to_string();

    let chars = str_value.chars();
    for char_value in &chars {
        println!("char: {}", char_value);
    }
}
Run Code Online (Sandbox Code Playgroud)
error[E0277]: `&std::str::Chars<'_>` is not an iterator
 --> src/main.rs:5:23
  |
5 |     for char_value in &chars {
  |                       -^^^^^
  |                       |
  |                       `&std::str::Chars<'_>` is not an iterator
  |                       help: consider removing the leading `&`-reference
  |
  = help: the trait `std::iter::Iterator` is not implemented for `&std::str::Chars<'_>`
  = note: `std::iter::Iterator` is implemented for `&mut std::str::Chars<'_>`, but not for `&std::str::Chars<'_>`
  = note: required by `std::iter::IntoIterator::into_iter`
Run Code Online (Sandbox Code Playgroud)

可变引用

fn main() {
    let str_value: String = "abc".to_string();

    let mut chars = str_value.chars();
    for char_value in &mut chars {
        println!("char: {}", char_value);
    }

    // why chars equal ""?
    assert_eq!(chars.as_str(), "");
}
Run Code Online (Sandbox Code Playgroud)
char: a
char: b
char: c
Run Code Online (Sandbox Code Playgroud)

phi*_*mue 5

charsis 的类型Chars实现了(“is a”)迭代器,其元素的类型为char

for在 Rust 中,您可以在实现(“是”)迭代器的事物上使用-loops 。

因此,您的第一个示例包含在以下内容中:Iterates over chars。

第二个示例不起作用,因为&chars它的类型&Chars(借用的、不可变的引用)没有实现Iterator.

然而,在第三个示例中,您有&mut Chars,这是一个迭代器

impl<I: Iterator + ?Sized> Iterator for &mut I {
    type Item = I::Item;
    fn next(&mut self) -> Option<I::Item> { (**self).next() }
    // some details omitted
}
Run Code Online (Sandbox Code Playgroud)

上面说:对于任何类型I,它是一个Iterator并且可能不满足?Sized(所有这些都适用于类型Chars),该类型&mut I是一个Iterator,其迭代值与原始迭代类型()相同type Item = I::Item,并且委托next(以及其他一些方法)到原始迭代器。

因此,第三个示例看到&mut Chars,知道CharsIterator,并推断 then&mut Chars也是Iterator可以在for循环中使用的 。

as_str-- 根据其文档(参见那里的示例)为您提供了剩余的(即尚未迭代的)子字符串,因此在迭代之后,它应该只是说""(即空),因为没有什么可以迭代的了。