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

如何在C#中分步过滤JSON数组并获取指定属性关联详情?

问题

我有一个多层结构的JSON数组(示例如下),需要分两步过滤:

  1. 按顶级属性env(例如值为ENG)筛选,得到对应环境的完整数据;
  2. 在第一步的结果中,按子对象的Id或Name属性(例如Name=TestA)筛选,获取对应的完整详情对象。

请问在C#中实现该需求的最佳方式是什么?

示例JSON数组:

[
    {
        "env": "ENG",
        "details": [
            {
                "Id": 3,
                "Name": "TestA",
                "programs": [
                    {
                        "name": "TestA",
                        "type": "AA"
                    }
                ]
            },
            {
                "tenantId": 5,
                "tenantName": "Demo",
                "programs": [
                    {
                        "name": "DEMO",
                        "type": "BB"
                    },
                    {
                        "name": "DEMO2",
                        "type": "BB"
                    }
                ]
            }
        ]
    },
    {
        "env": "Span",
        "details": [
            {
                "tenantId": 4,
                "tenantName": "Cat",
                "programs": [
                    {
                        "name": "CAT",
                        "type": "123"
                    }
                ]
            },
            {
                "tenantId": 5,
                "tenantName": "Demo",
                "programs": [
                    {
                        "name": "DEMOSpan",
                        "type": "www"
                    },
                    {
                        "name": "DEMOU2",
                        "type": "eee"
                    }
                ]
            }
        ]
    }
]

第一步筛选预期结果:

{
    "env": "ENG",
    "details": [
        {
            "Id": 3,
            "Name": "TestA",
            "programs": [
                {
                    "name": "TestA",
                    "type": "AA"
                }
            ]
        },
        {
            "tenantId": 5,
            "tenantName": "Demo",
            "programs": [
                {
                    "name": "DEMO",
                    "type": "BB"
                },
                {
                    "name": "DEMO2",
                    "type": "BB"
                }
            ]
        }
    ]
}

第二步筛选预期结果:

{
    "Id": 3,
    "Name": "TestA",
    "programs": [
        {
            "name": "TestA",
            "type": "AA"
        }
    ]
}
解决方案

在C#中,推荐两种实现方式,可根据场景选择:

方式一:强类型模型解析(推荐,类型安全)

先根据JSON结构定义对应实体类,再用System.Text.Json(.NET Core 3.0+内置)或Newtonsoft.Json完成序列化与筛选,这种方式能获得编译时类型检查,降低运行时错误。

1. 定义实体类

// 顶级环境数据对象
public class EnvData
{
    public string Env { get; set; }
    public List<DetailItem> Details { get; set; }
}

// 详情子对象(部分属性为可选,需用可空类型)
public class DetailItem
{
    public int? Id { get; set; }
    public string Name { get; set; }
    public int? TenantId { get; set; }
    public string TenantName { get; set; }
    public List<Program> Programs { get; set; }
}

// 程序子对象
public class Program
{
    public string Name { get; set; }
    public string Type { get; set; }
}

2. 实现筛选逻辑

以System.Text.Json为例:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text.Json;

class Program
{
    static void Main()
    {
        string jsonStr = "你的JSON字符串内容";
        
        // 反序列化为强类型列表
        var envDataList = JsonSerializer.Deserialize<List<EnvData>>(jsonStr);
        
        // 第一步:按env筛选目标环境数据
        var targetEnvData = envDataList.FirstOrDefault(data => 
            data.Env.Equals("ENG", StringComparison.OrdinalIgnoreCase));
        
        if (targetEnvData == null)
        {
            Console.WriteLine("未找到指定环境的数据");
            return;
        }
        
        // 第二步:按Id或Name筛选目标详情项
        var targetDetail = targetEnvData.Details.FirstOrDefault(item => 
            item.Id == 3 || item.Name?.Equals("TestA", StringComparison.OrdinalIgnoreCase) == true);
        
        if (targetDetail != null)
        {
            // 输出格式化后的结果
            string resultJson = JsonSerializer.Serialize(targetDetail, new JsonSerializerOptions { WriteIndented = true });
            Console.WriteLine(resultJson);
        }
        else
        {
            Console.WriteLine("未找到指定的详情项");
        }
    }
}

方式二:动态类型/JObject解析(无需定义实体类,快速处理)

如果是临时脚本或快速验证场景,可直接用Newtonsoft.Json的JObject动态处理,无需提前定义实体类:

using Newtonsoft.Json.Linq;
using System;
using System.Linq;

class Program
{
    static void Main()
    {
        string jsonStr = "你的JSON字符串内容";
        
        // 解析为JArray
        var jsonArray = JArray.Parse(jsonStr);
        
        // 第一步:筛选env为ENG的对象
        var targetEnvObj = jsonArray.FirstOrDefault(obj => 
            obj["env"]?.ToString().Equals("ENG", StringComparison.OrdinalIgnoreCase) == true);
        
        if (targetEnvObj == null)
        {
            Console.WriteLine("未找到指定环境的数据");
            return;
        }
        
        // 第二步:筛选Name为TestA或Id为3的详情项
        var detailsArray = targetEnvObj["details"] as JArray;
        var targetDetail = detailsArray.FirstOrDefault(item => 
            item["Id"]?.Value<int>() == 3 || item["Name"]?.ToString().Equals("TestA", StringComparison.OrdinalIgnoreCase) == true);
        
        if (targetDetail != null)
        {
            Console.WriteLine(targetDetail.ToString(Newtonsoft.Json.Formatting.Indented));
        }
        else
        {
            Console.WriteLine("未找到指定的详情项");
        }
    }
}

注意事项

  • 强类型方式适合长期维护的项目,能避免拼写错误和类型不匹配问题;
  • 动态类型方式适合快速验证,但缺少类型安全,需注意空值判断避免空引用异常;
  • 筛选时可根据需求选择是否忽略大小写,示例中用StringComparison.OrdinalIgnoreCase实现忽略大小写匹配。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.17 18:13:21