将关联的非可变常量数据分配给枚举变体

问题描述

注意: 我的问题类似于这个问题,但似乎没有解决我的用例。 Can enum variants have constant associated values?

问题说明

我的服务器返回一个国家/地区(很长的列表),该国家/地区在内部映射到一个枚举(提前知道一组封闭的有效可能性)。

我需要一些与国家相关的数据(例如语言)。

关联数据是“恒定的”,出于人体工程学/性能原因,将数据“附加”到枚举变体是有意义的。

人为的例子:

我有一个语言列表和一个国家列表

#[derive(Serialize,Deserialize)
enum Language {
  English,Spanish,french,// .. 100 more
}

#[derive(Serialize,Deserialize)
enum Country {
  USA,England,France,Mexico,Spain
// .. 100 more
}

内部我希望枚举隐式地将语言值与国家/地区相关联:

// what I want

#[derive(Serialize,Deserialize)
enum Country {
  USA(Language),England(Language),// ... more countries with associated languages...
}

  1. 在创建“国家/地区”时,我不想提供语言,而只想提供 Country::country_name(没有语言)
  2. 在序列化/反序列化时,应隐式添加语言

查看 serde.rs 文档,您可以添加字段属性

#[serde(default)]

#[serde(default = "path")]

但是

  1. default 没有适用于所有国家/地区的认语言 - 而是取决于它所包含的国家/地区变体
  2. path - 调用函数时不带国家/地区值,因此效果default
  3. 类似

我考虑过的一些选择

  1. 手动实现序列化/反序列化 - 但我有很多情况并且容易出错
  2. 懒惰的常量值?详细

解决方法

不是理想的解决方案,但在我的用例中是合理的:

使用 lazy_staticconst 数据(在我的情况下,根据问题中的示例,数据不是常量)

impl Country {
  fn language() -> '&static Language { // my language is more complex than just a simple type described in this question so i do want to have static instances . understandably in the answer it seems overkill
     match self {
        USA => {
          lazy_static! {
             let lang: Language = Language::English; /// in reality more data here...
          }
          &lang
        }
        France => { ...}
        // ... more countries
     }
  }
}