C# 如何从JSON反序列化不同类型的数组

C# 如何从JSON反序列化不同类型的数组,c#,json,C#,Json,我有一个JSON字符串,看起来像: { "type": "group", "logicalOperator": "or", "conditions":[{ "type": "condition", "metric": "CTR", "operator": ">=", "value": "123" }, { "type

我有一个JSON字符串,看起来像:

{
    "type": "group",
    "logicalOperator": "or",
    "conditions":[{
            "type": "condition",
            "metric": "CTR",
            "operator": ">=",
            "value": "123"
        },
        {
            "type": "group",
            "logicalOperator": "and",
            "conditions": [{
                "type": "condition",
                "metric": "CTR",
                "operator": ">=",
                "value": "123"
                }]
        }
    ]
}
我想将其反序列化为C类(使用
Newtonsoft.JSON
)。但是
条件
可以包括
条件
这一点给我带来了问题

public class Group {
    public string logicalOperator { get; set; }
    public List<object> conditions { get; set; }
}

public class Condition {
    public string metric { get; set; }
    public string @operator { get; set; }
    public int value { get; set; }
}
公共类组{
公共字符串逻辑运算符{get;set;}
公共列表条件{get;set;}
}
公共阶级状况{
公共字符串度量{get;set;}
公共字符串@运算符{get;set;}
公共int值{get;set;}
}
如何摆脱
列表
?蒂亚

首先,C#不反序列化json字符串。C#可用于调用执行以下操作的库

基于纯粹的猜测,我会继续说,您可能正在使用
Newtonsoft.Json
进行反序列化,尽管您可能正在使用其他东西。让我们后退一步

如果是这样,那么“摆脱”列表将是你最不关心的问题。事实上,你的第一个挑战是,你是否能够找到不只是空的、简单的“ol
System.Object
实例”的实例。这仅仅是因为告诉反序列化程序你的超级(基本)类型是什么,甚至不会让他们去寻找可能的子类型,因为任何类型的子类型都是一个开放集(任何人都可以引用你的程序集并扩展你的类,而你却感觉不到任何东西)

拥有一个类型为
System.Object
的引用列表,每个引用都指向类型为
MyNamespace.Group
MyNamespace.Condition
的实例,直到您意识到拥有
MyNamespace.Group
的实例,而另一个则是您在这个特定用例中面临的实际挑战描述

再退一步,在OOP中,每当您想要存储可能不同类型实例的列表,并且您的语言是强类型的,并且提供某种泛型(包括C#),对于元素类型,您不能有一个泛型参数,该参数不能从您希望实例可能具有的每个特定类型隐式赋值。在您的情况下,
对象
与多个
条件
兼容。如果这是您唯一的问题,那么您应该简单地创建第三个类(我们称之为
EitherGroupOrCondition
),并将其作为自然发生的类层次结构的根(
Group
Condition
现在都应该扩展
EitherGroupOrCondition
)。然后您可以将
列表
转换为
列表

回到反序列化:您需要查看
JsonSerializerSettings.typenameholling
及其相关特性

你应该考虑以下的前提条件来实现你的目标:

  • 彻底理解OOP
  • 了解特定Json反序列化程序的功能(希望您使用的是
    Newtonsoft.Json
这两个先决条件都需要时间和耐心,我鼓励您继续并满足它们,不要盲目工作,至少不了解您正在使用的产品的建议表面。

您没有问题:

public class YourType
{
    public ConditionType Type { get; set; }
    public string Metric { get; set; }
    public string Operator { get; set; }
    public int Value { get; set; }
    public string LogicalOperator { get; set; }

    public List<YourType> Conditions { get; set; }
}

public enum ConditionType
{
    Group,
    Condition
}
public类类型
{
公共条件类型类型{get;set;}
公共字符串度量{get;set;}
公共字符串运算符{get;set;}
公共int值{get;set;}
公共字符串逻辑运算符{get;set;}
公共列表条件{get;set;}
}
公共枚举条件类型
{
集团,,
条件
}
然后像平常一样反序列化它

var result = JsonConvert.DeserializeObject<YourType>(yourJson);
var result=JsonConvert.DeserializeObject(yourJson);
您将得到一个
YourType
类,该类具有一个枚举器
Type
,您可以使用该枚举器确定它是一个组还是一个条件

如果是条件,则填写属性


如果它是一个组,您的
条件
内部列表包含其余部分。

的可能重复项请查看此项,我已将此项标记为可能重复项。因为您的问题看起来像是条件反序列化。假设你可以使用,看一看和可能的副本谢谢你的回答。我想到了那个变体。但我想检查null的属性可以了解它是哪个类——这是一种糟糕的做法。特别是当我们谈论像C#(OOP)这样的语言时,你没有检查null。您正在检查类型enum propertyAh,yes。错过了。好的,泰。