如何创建列和行明智的json结构?

时间:2016-08-19 13:21:52

标签: c# .net json linq

我正在尝试创建如下所示的json结构:

{
  "cols": [
    {
      label: "Types",
      type: "string"
    },
    {
      label: "values",
      type: "number"
    }
  ],
  "rows": [
    {
      c: [
        {
          v: "Mushrooms"
        },
        {
          v: 3
        },

      ]
    },
    {
      c: [
        {
          v: "Olives"
        },
        {
          v: 31
        }
      ]
    },
    {
      c: [
        {
          v: "Zucchini"
        },
        {
          v: 1
        },

      ]
    },
    {
      c: [
        {
          v: "Pepperoni"
        },
        {
          v: 2
        },

      ]
    }
  ]
}

以上是我从这里得到的值:

public class Type
{
    public int Mushrooms { get; set; }
    public int Olives { get; set; }
    public int Zucchini { get; set; }
    public int Pepperoni { get; set; }
  public int Statistics { get; set; } //Ignore properties in final output
    public int Count { get; set; } //Ignore properties in final output
    public int Average { get; set; } //Ignore properties in final output
}

var types = MyRepository<Type>.FirstorDefault();

以上查询输出:

  

蘑菇:3

     

橄榄:31等。

这就是我设计课程的方式:

public class Cols
{
    public List<Names> Names { get; set; }

}

public class Names
{
    public string label { get; set; }
    public string type { get; set; }
}

但我得到的输出是这样的:

"data": [
    {
      "Names": [
        {
          "label": "Types",
          "type": "string"
        },
        {
          "label": "values",
          "type": "number"
        }
      ]
    }
  ]

更新:班级设计

 public class Rootobject
    {
        public List<Names> cols { get; set; }
        public List<Row> rows { get; set; }
    }

    public class Names
    {
        public string label { get; set; }
        public string type { get; set; }
    }

    public class Row
    {
        public List<C> c { get; set; }
    }

    public class C
    {
        public object v { get; set; } 
    }

仍然高于类设计让我在json结构下面:

{
  "Data": {
    "cols": [
      {
        "label": "Types",
        "type": "string"
      },
      {
        "label": "values",
        "type": "number"
      }
    ],
    "rows": [
      {
        "c": [
          {
            "v": "Mushrooms"
          },
          {
            "v": "3"
          },
          {
            "v": "Olives"
          },
          {
            "v": "31"
          },
          {
            "v": "Zucchini"
          },
          {
            "v": "1"
          },
          {
            "v": "Pepperoni"
          },
          {
            "v": "2"
          }
        ]
      }
    ]
  }
}

对于返回json数据,我正在使用这个json类的asp.net mvc。

return Json(new {Data = rootObject }, JsonRequestBehavior.AllowGet);

3 个答案:

答案 0 :(得分:1)

根据你的第一个json,如果你想以这种方式序列化你的类结构应该是这样的:

public class Rootobject
{
    public List<Names> cols { get; set; }
    public List<Row> rows { get; set; }
}

public class Names
{
    public string label { get; set; }
    public string type { get; set; }
}

public class Row
{
    public List<C> c { get; set; }
}

public class C
{
    public string v { get; set; }
}

答案 1 :(得分:1)

您更新的课程设计可以代表您需要的JSON。问题是,如何分配和初始化Rootobject的内容?您可以使用reflection执行此操作,特别是使用Type.GetProperties()循环浏览Rootobject的所有公共属性,然后使用PropertyInfo.GetValue()查询值,如下所示:

var query = types.GetType()
    .GetProperties(BindingFlags.Instance | BindingFlags.Public)
    .Where(p => p.GetIndexParameters().Length == 0 && p.GetGetMethod() != null && p.CanRead)
    .Select(p => new Row { c = new List<C> { new C { v = p.Name }, new C { v = p.GetValue(types, new object[0]) } } });

var root = new Rootobject
{
    cols = new List<Names> { new Names { label = "Types", type = "string" }, new Names { label = "values", type = "number" } },
    rows = query.ToList(),
};

return Json(root, JsonRequestBehavior.AllowGet);

示例fiddle

如果您有一个要忽略的特定属性名称列表,您可以将这些名称添加到哈希集并过滤掉它们:

var ignoredPropertyNames = new HashSet<string> { "Statistics", "Average", "Count" };

var query = types.GetType()
    .GetProperties(BindingFlags.Instance | BindingFlags.Public)
    .Where(p => p.GetIndexParameters().Length == 0 && p.GetGetMethod() != null && p.CanRead)
    .Where(p => !ignoredPropertyNames.Contains(p.Name))
    .Select(p => new Row { c = new List<C> { new C { v = p.Name }, new C { v = p.GetValue(types, new object[0]) } } });

或者,如果您要包含特定的属性名称列表,则可以使用Type.GetProperty(string)获取相应的属性并按以前的方式继续:

var propertyNames = new[] { "Mushrooms", "Olives", "Zucchini", "Pepperoni" };

var query = propertyNames
    .Select(n => types.GetType().GetProperty(n))
    .Where(p => p != null)
    .Where(p => p.GetIndexParameters().Length == 0 && p.GetGetMethod() != null && p.CanRead)
    .Select(p => new Row { c = new List<C> { new C { v = p.Name }, new C { v = p.GetValue(types, new object[0]) } } });

答案 2 :(得分:0)

如前所述,here您可以对动态对象进行反序列化并使用该对象,这样可以避免在不需要的地方编写免费代码:

dynamic obj = JObject.Parse(yourComplexJson);