2012-11-29 214 views
3

我有这样一个JSON:解析复杂的JSON对象用C#

{ 
    "name" : "MyCustomName", 
    "my_node" : { 
     "name" : "my_node_name" 
    }, 
    "dict1":"value1", 
    "dict2":"value2", 
    "dict3":"value3", 
    ... 
} 

和对象:

class Node{ 
    string value; 
} 

class Sample:IDictionary<string, string>{ 
    Node node; 
    string name; 
} 

节点名称在Sample类总是存在。 事情是我不知道会有多少“dictN”字段......这就是要点。

问题是: 如何将该JSON反序列化为此对象?

+2

这很好,你有一个问题......问题是? =) –

+0

伟大的问题:) –

+1

你有控制如何创建JSON。你可以使用一个数组是“字典”:[“val1”,“val2”,“val3 ...”]? – Pinetree

回答

2

编辑:显然,即使字段名称协调一致,您的反序列化器也无法应付与通用字典字段结合的特定字段。

在这种情况下,我只是劝反序列化作为Dictionary<string, object>和建筑与结果:

var d = new JavaScriptSerializer().Deserialize<Dictionary<string, object>>(json); 
Sample s = new Sample(); 
s.name = (string)d["name"]; 
Node n = new Node(); 
n.value = (string)((Dictionary<string, object>)d["my_node"])["name"]; 
foreach (var key in d.Keys.Except(new string[] { "name", "my_node" })) 
{ 
    s.Add(key, (string)d[key]); 
} 
+0

关于班级的变化,这没有任何问题。我可以将Sample.node更改为Sample.my_node,对于值相同 –

+0

尝试一下,看看它是否有效,然后...... TBH如果能够成功地决定“此值在某个字段中发生,我会感到惊讶,这个值在继承的字典中“。 – Rawling

+0

它仍然没有工作,是关于通过正确的值(收集)和有时在左边(领域)传递值可以混淆的问题:/ –

1

最初的想法

下面是一本字典串行器。它有一个不接受空字符串的特殊情况。

private void SerializePerinatalModel<T>(IDictionary<string, object> dataModel, T perinatalModel) 
    { 
     Type sourceType = typeof(T); 
     foreach (PropertyInfo propInfo in (sourceType.GetProperties())) 
     { 
      if (dataModel.ContainsKey(propInfo.Name)) 
      { 
       // if an empty string has been returned don't change the value 
       if (dataModel[propInfo.Name].ToNullSafeString() != String.Empty) 
       { 
        try 
        { 
         Type localType = propInfo.PropertyType; 
         localType = Nullable.GetUnderlyingType(localType) ?? localType; 
         propInfo.SetValue(perinatalModel, Convert.ChangeType(dataModel[propInfo.Name], localType), null); 
        } 
        catch (Exception e) 
        { 
         // ToDo: log update value errors 
        } 

       } 
      } 

     } 
    } 

但是可以设置为null安全。它处理可空类型。

由于JSON本质上是一种字典类型,因此通过顶层类型进行迭代应该可以达到目的。

这是写得很快,所以只是一个想法的草图。

更好的主意 同时尝试使用

foreach (var item in JsonData.Where(m => m.Key.Substring(0,4) == "dict")) 
{ 
    // add item to collection 
} 

也可能做的BIZ。

1

您可以简单地以Dictionary<string, object>的形式输出,请尝试使用这段代码。

System.Web.Script.Serialization.JavaScriptSerializer s = 
    new System.Web.Script.Serialization.JavaScriptSerializer(); 

var nodes = s.Deserialize<Dictionary<string, object>>(jsonString); 
var dictNodes = nodes.Where(w => w.Key.StartsWith("dict")); 
+0

好的....也许我的例子不是很好......但如果会有像“mydict1”这样的字段呢。我只专注于只有两个领域,我相信总是其余的应该进入容器。 –

+1

所以你可以用我的代码来实现它。其实质在于这一行代码'nodes.Where(w => w.Key.StartsWith(“dict”));'这将在过滤后为您提供所有具有dictN元素的节点。 –