gpt4 book ai didi

rust - 在vec中验证带有关联值的枚举的唯一性

转载 作者:行者123 更新时间:2023-12-03 11:33:18 27 4
gpt4 key购买 nike

在下面的代码中,我定义了一种输入类型为Vec<Food>的方法。此方法应在不检查关联值的情况下验证 ARM 是否必须唯一。这意味着它最多应包含1个比萨饼,1个蛋糕和1个地铁。 注意:不需要所有臂都在Vec中。我也在下面的代码中编写了一些测试,它们仍然需要通过。

我的“真实”代码中有更多枚举类,而我目前的方式伸缩性不佳,所以我希望有一种更简单的方式。

fn main() {

}

enum Food {
Cake(String),
Pizza(i32),
Subway(u64)
}

struct CustomError;

fn validate(foods: Vec<Food>) -> Result<(), CustomError> {
let mut cake = false;
let mut pizza = false;
let mut subway = false;

for f in foods.iter() {
match f {
Food::Cake(_) => {
if cake {
return Err(CustomError)
}

cake = true;
},
Food::Pizza(_) => {
if pizza {
return Err(CustomError)
}

pizza = true;
},
Food::Subway(_) => {
if subway {
return Err(CustomError)
}

subway = true;
},
}
}

Ok(())
}

#[cfg(test)]
mod tests {
use super::*;

#[test]
fn test() {
assert!(validate(vec![Food::Pizza(1)]).is_ok());
assert!(validate(vec![Food::Pizza(1), Food::Cake("Apple".to_owned())]).is_ok());
assert!(validate(vec![]).is_ok());

assert!(validate(vec![Food::Pizza(1), Food::Pizza(1)]).is_err());
assert!(validate(vec![Food::Pizza(1), Food::Pizza(2)]).is_err());
}
}

最佳答案

为了在不关心任何关联数据的情况下比较enum变体,函数 std::mem::discriminant 非常有用。给定enum类型的值,std::mem::discriminant返回 std::mem::Discriminant 类型的值,该值指示该值是哪个变体。 std::mem::Discriminant实现Hash,因此我们可以将到目前为止已经看到的所有变体保留在HashSet中,以检查是否存在重复项。

只是一个小技巧:HashSet::insert返回一个 bool 值,当插入的元素尚未在集合中时为true。这意味着我们可以结合以下步骤:检查是否已看到判别式,然后插入新的判别式。

use std::collections::HashSet;
use std::mem::discriminant;

enum Food {
Cake(String),
Pizza(i32),
Subway(u64),
}

struct CustomError;

fn validate(foods: Vec<Food>) -> Result<(), CustomError> {
let mut discriminants = HashSet::new();
for food in foods {
if !discriminants.insert(discriminant(&food)) {
return Err(CustomError);
}
}
Ok(())
}

(playground)

关于rust - 在vec中验证带有关联值的枚举的唯一性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/59587314/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com