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

如何用Serde将多个Vec序列化为单个JSON数组?

解决方案

核心思路

先把workspace和methods的元素合并为一个统一的可序列化集合,再一次性将这个集合序列化为resources字段,彻底避免重复调用serialize_field导致的覆盖问题。

具体实现

假设Workspace和Request已实现Serialize trait,以下是完整代码示例:

1. 定义基础结构体

use serde::{Serialize, Serializer};
use serde::ser::SerializeStruct;

#[derive(Serialize)]
struct Workspace<'a> {
    name: &'a str,
    // 其他业务字段
}

#[derive(Serialize)]
struct Request<'a> {
    path: &'a str,
    // 其他业务字段
}

struct Base<'a> {
    workspace: Vec<Workspace<'a>>,
    methods: Vec<Request<'a>>,
    // 其他可选字段
}

2. 为Base实现Serialize trait

impl<'a> Serialize for Base<'a> {
    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
    where
        S: Serializer,
    {
        // 初始化结构体序列化器,参数为结构体名称和字段总数(含其他字段需调整数值)
        let mut state = serializer.serialize_struct("Base", 1)?;
        
        // 合并两个Vec的迭代器,转换为统一类型的集合
        let resources = self.workspace.iter()
            .chain(self.methods.iter())
            .collect::<Vec<_>>();
        
        // 一次性序列化合并后的集合作为resources字段
        state.serialize_field("resources", &resources)?;
        
        // 完成结构体序列化
        state.end()
    }
}

进阶优化(避免额外内存分配)

如果不想通过collect分配新的Vec,可以自定义一个枚举类型包装两种元素,为枚举实现Serialize后直接使用迭代器序列化:

// 自定义枚举统一两种元素类型
enum Resource<'a> {
    Workspace(&'a Workspace<'a>),
    Request(&'a Request<'a>),
}

impl<'a> Serialize for Resource<'a> {
    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
    where
        S: Serializer,
    {
        match self {
            Resource::Workspace(w) => w.serialize(serializer),
            Resource::Request(r) => r.serialize(serializer),
        }
    }
}

// 调整Base的Serialize实现
impl<'a> Serialize for Base<'a> {
    fn serialize<S>(&self, serializer: S) -> Result<S::Ok, S::Error>
    where
        S: Serializer,
    {
        let mut state = serializer.serialize_struct("Base", 1)?;
        
        // 直接生成枚举迭代器,无需分配新Vec
        let resources = self.workspace.iter().map(Resource::Workspace)
            .chain(self.methods.iter().map(Resource::Request));
        
        state.serialize_field("resources", &resources.collect::<Vec<_>>())?;
        state.end()
    }
}

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.10 11:16:11