为什么解构借用的枚举需要取消引用其字段?

Why does destructuring a borrowed Enum require dereferencing its fields?

考虑以下片段:

use std::fmt;

enum TestEnum {
    StructMem {value: i32, is_valid: bool},
    RandoMem,
}

impl fmt::Display for TestEnum {
    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
        use TestEnum::*;
        match self {
            StructMem {value, is_valid} => {
                if *is_valid { // Why dereference is_valid ?
                    write!(f, "f")?
                }
                write!(f, "{:?}", value)
            }
            RandoMem => {
                f.write_str("Random")
            }
        }
    }
}

为什么我需要在 if 语句中取消引用 is_valid

编辑:这个问题似乎是在处理类似的情况,但答案都集中在解决具体问题(不涉及struct) 并且没有解释 ownership/binding 语义。

这不是特定于 matchenum 而是由于 fmt() 的签名,它以 self 作为参考(&self 而不是 self,如果所有权被拿走了)。

因此,match self 已经引用了 TestEnum 的借用实例,匹配臂 StructMem {value, is_valid} 通过引用(&i32&bool).这就是为什么 is_valid 最终成为 &bool,而不是 bool

当您对引用进行模式匹配并解构它时,您只能获得内部成员的引用,否则您会将内部成员从不可变引用中移出,这将违反 Rust 的所有权规则。这是一个更简单的例子:

struct Container(Vec<i32>);

fn get_inner_vec(c: &Container) -> &Vec<i32> {
    // v MUST BE a reference
    // otherwise this destructing would somehow be moving the Vec
    // outside of an immutable borrow of Container
    let Container(v) = c;
    v
}