简体   繁体   中英

Complex inheritance pattern in (JSON) data contracts

I have to handle serialized data that can take the following forms:

{
    "CommonKey" : "Value",
    "ObjType" : "A",
    "Obj" : {
        "CommonObjKey" : "Value"
        "ObjKey" : "Value"
    }
}

OR

{
    "CommonKey" : "Value",
    "ObjType" : "B",
    "Obj" : {
        "CommonObjKey" : "Value"
        "ObjKey" : 1234
    }
}

Notice that ObjKey can either be a string or integer depending on type.

If overloading derived return types was allowed in C#, this is how it would be modeled:

abstract class ContractBase 
{ 
    string CommonKey;
    string ObjType;
    abstract ObjBase Obj; 
}

class AContract : ContractBase { override AObj Obj; }
class BContract : ContractBase { override BObj Obj; }

abstract class ObjBase { string CommonObjKey; }

class AObj : ObjBase { string ObjKey; }
class BObj : ObjBase { int ObjKey; }

Is there a recommended way to model this data pattern? Requirements are:

  1. I can easily deserialize it using JSON.NET
  2. I can use the base types 90% of the time and only cast it when A or B-specific fields are needed.

I would suggest using dyanmic for the one property ( ObjKey ) that doesn't have a consistent type.

Possible implementation:

var cb1 = new ContractBase
{
    CommonKey = "Value",
    ObjType = "A",
    Obj = new Obj
    {
        CommonObjKey = "Value",
        ObjKey = 1234
    }
};

var cb2 = new ContractBase
{
    CommonKey = "Value",
    ObjType = "A",
    Obj = new Obj
    {
        CommonObjKey = "Value",
        ObjKey = "Value"
    }
};

class ContractBase 
{
    public string CommonKey { get; set; }
    public string ObjType { get; set; }
    public Obj Obj { get; set; }
}

class Obj
{
    public string CommonObjKey { get; set; }
    public dynamic ObjKey { get; set; }
}

Note that you could use object instead of dynamic , but dynamic reduces the need for casting, which makes code more readable and easy to understand.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM