You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Rust中Struct方法创建及所有权移动报错的解决办法

解决Rust中Struct初始化时的所有权移动问题

你的代码出现use of moved value错误,核心原因是:DaysOfTheWeekNames枚举没有实现Copy trait,当你在Self { day, ... }中使用day时,变量的所有权已经被转移到结构体的day字段里,后续调用Weekday::isWeekend(day)时,这个变量已经不再属于当前作用域,因此报错。

同时注意你原来的isWeekend逻辑是反的——周六周日应该被判定为周末(返回true),下面的解决方案会一并修正这个问题。

方案一:给枚举添加Copy和Clone派生宏

你的枚举是无关联数据的单元枚举,完全可以安全地复制。通过派生Copy和Clone,传递参数时会自动复制一份,不会转移所有权:

#[derive(Debug, Copy, Clone)]
enum DaysOfTheWeekNames {
    Friday,
    Saturday,
    Sunday,
}

#[derive(Debug)]
struct Weekday {
    day: DaysOfTheWeekNames,
    weekend: bool,
}

impl Weekday {
    fn is_weekend(day: DaysOfTheWeekNames) -> bool {
        matches!(day, DaysOfTheWeekNames::Saturday | DaysOfTheWeekNames::Sunday)
    }
    
    fn new_day(day: DaysOfTheWeekNames) -> Self {
        Self { 
            day, 
            weekend: Self::is_weekend(day) 
        }
    }
}

fn main() {
    let today = Weekday::new_day(DaysOfTheWeekNames::Saturday);
    println!("Today: {:#?}", today);
}

这里用matches!宏简化了周末判断的逻辑,同时遵循Rust的蛇形命名规范把isWeekend改成is_weekend。

方案二:让is_weekend接收引用而非所有权

如果不想给枚举添加Copy,可以修改方法参数为引用类型,这样只借用变量而不转移所有权:

#[derive(Debug)]
enum DaysOfTheWeekNames {
    Friday,
    Saturday,
    Sunday,
}

#[derive(Debug)]
struct Weekday {
    day: DaysOfTheWeekNames,
    weekend: bool,
}

impl Weekday {
    fn is_weekend(day: &DaysOfTheWeekNames) -> bool {
        matches!(day, DaysOfTheWeekNames::Saturday | DaysOfTheWeekNames::Sunday)
    }
    
    fn new_day(day: DaysOfTheWeekNames) -> Self {
        Self { 
            day, 
            weekend: Self::is_weekend(&day) 
        }
    }
}

fn main() {
    let today = Weekday::new_day(DaysOfTheWeekNames::Saturday);
    println!("Today: {:#?}", today);
}

这种方式更适合无法实现Copy的复杂枚举,同样能解决所有权问题。

方案三:调整执行顺序(不推荐)

如果必须转移所有权给is_weekend,可以让方法返回判定结果和原变量,再用于结构体初始化,但这种写法冗余,一般不推荐:

#[derive(Debug)]
enum DaysOfTheWeekNames {
    Friday,
    Saturday,
    Sunday,
}

#[derive(Debug)]
struct Weekday {
    day: DaysOfTheWeekNames,
    weekend: bool,
}

impl Weekday {
    fn is_weekend(day: DaysOfTheWeekNames) -> (bool, DaysOfTheWeekNames) {
        let is_weekend = matches!(&day, DaysOfTheWeekNames::Saturday | DaysOfTheWeekNames::Sunday);
        (is_weekend, day)
    }
    
    fn new_day(day: DaysOfTheWeekNames) -> Self {
        let (weekend, day) = Self::is_weekend(day);
        Self { day, weekend }
    }
}

fn main() {
    let today = Weekday::new_day(DaysOfTheWeekNames::Saturday);
    println!("Today: {:#?}", today);
}

推荐写法

优先选择方案一,因为单元枚举实现Copy/Clone没有任何副作用,代码最简洁直观,完全符合你的需求。

内容的提问来源于stack exchange,提问作者imharjyotbagga

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.03 01:10:29