如果这是基本的,请原谅我,我对Rust 还很陌生.我正在try 创建一些struct来模仿外部API.在外部API中,有一个属性可以是数字,也可以是字符串.在打印脚本中,我可以这样做:

interface ApiParams {
  thing: string | number;
}

在Rust中,我想对struct中的thing属性做同样的事情,但我找不到任何这样的方法,或者动态类型的例子,或者与我试图在这里做的非常匹配的问题.允许动态类型似乎与rust的类型安全特性背道而驰,但我仍然需要在我的API和数据库中允许这一点,以匹配外部API.

我试过这个:

pub enum Thing {
    CouldBeANumber(u8),
    CouldBeAString(String),
}

struct ExternalApiThing {
  thing: Thing
}

但是当我发布到我的API时,我收到了这样的错误

Json deserialize error: unknown variant 'the string that was posted', expected 'CouldBeANumber' or 'CouldBeAString' at line 1 column 1921

很明显,我不明白如何创建一个枚举,这样我就可以使用任何数字或任何字符串.

一个人如何在Rust 中做到这样的事情呢?

推荐答案

如果您在这里使用Serde,那么在默认情况下,它会将枚举序列化为JSON对象,因此您将看到以下内容:

{"thing":{"CouldBeANumber":2}}
{"thing":{"CouldBeAString":"boo"}}%

显然,这不是您想要的,因此您希望将Thing声明为未标记:

use serde::{Serialize, Deserialize};

#[derive(Serialize, Deserialize)]
#[serde(untagged)]
pub enum Thing {
    CouldBeANumber(u8),
    CouldBeAString(String),
}

#[derive(Serialize, Deserialize)]
struct ExternalApiThing {
  thing: Thing
}

fn main() {
    let thing1 = ExternalApiThing { thing: Thing::CouldBeANumber(2) };
    let thing2 = ExternalApiThing { thing: Thing::CouldBeAString("boo".into()) };
    let _ = serde_json::to_writer(std::io::stdout(), &thing1);
    println!();
    let _ = serde_json::to_writer(std::io::stdout(), &thing2);
}

那么你得到的是这样的:

{"thing":2}
{"thing":"boo"}

…这就是你所希望的.The docs outline several other ways您可以序列化一个枚举,外加许多其他选项,您可以使用这些选项随心所欲地控制事物.我经常查阅它.

Rust相关问答推荐

在‘await’点上使用‘std::同步::Mutex’是否总是会导致僵局?

什么是Rust惯用的方式来使特征向量具有单个向量项的别名?

如果成员都实现特征,是否在多态集合上实现部分重叠的特征?

当第二个`let`依赖于第一个`let()`时,如何在一行中有多个`let()`?

通过解引用将值移出Box(以及它被脱糖到什么地方)?

新创建的变量的绑定生存期

Gtk4-rs:将监视器作为gdk::monitor获取,而不是作为glib::对象获取

在复制类型中使用std::ptr::WRITE_VILAR进行内部可变性的安全性(即没有UnSafeCell)

Rust ndarray:如何从索引中 Select 数组的行

随机函数不返回随机值

如何迭代存储在 struct 中的字符串向量而不移动它们?

Rust:为什么 Pin 必须持有指针?

Rust 中的 Option as_ref 和 as_deref 有什么不同

将原始可变指针传递给 C FFI 后出现意外值

产生拥有值的迭代器的 Rust 可变borrow 在循环中失败

如何解析 Rust 中的 yaml 条件字段?

我如何将 google_gmail1::Gmail> 传递给线程生成?

tokio async rust 的 yield 是什么意思?

为什么-x试图解析为文字并在声明性宏中失败?

加入动态数量的期货