【问题标题】:Convert deserialized json class to datatable将反序列化的 json 类转换为数据表
【发布时间】:2015-03-04 16:46:45
【问题描述】:

我正在尝试使用下面的代码将我反序列化为类的 json 转换为数据表,但是下面的代码在最后一行失败。

using (var webClient = new System.Net.WebClient())
{
    var downloadTable = webClient.DownloadString(url);
    var myTable = JsonConvert.DeserializeObject<leagueTable>(downloadTable);
    DataTable dt = myTable;
}

我知道我可以直接反序列化为数据表,但我想先将其反序列化为一个类,以便我可以操作数据并让使用该代码的其他人知道数据的结构。

JSON 是嵌套的,为它创建的类在下面

public class leagueTable
{
    public string leaguename { get; set; }
    public int gameday { get; set; }
    public System.Collections.ObjectModel.Collection<Ranking> ranking { get; set; }
}

public class Ranking
{
    public int rank { get; set; }
    public string club { get; set; }
    public int games { get; set; }
    public int points { get; set; }
}

【问题讨论】:

  • leagueTable 是否继承自 DataTable?还是某种集合类型?
  • 所以你的问题是“如何将任何对象转换为数据表”
  • 我已经编辑了你的标题。请参阅“Should questions include “tags” in their titles?”,其中的共识是“不,他们不应该”。
  • > 但是下面的代码在最后一行失败。你在最后一行得到什么错误?是类型不匹配吗?
  • @DStanley LeagueTable 是一个类的名称,它不继承自DataTable

标签: c# .net json class datatable


【解决方案1】:

为了将您的 json 字符串反序列化为 DataTable,它需要是一个 json 对象数组,其中数组中的每个第一级对象对应一行。 例如,这可以正常工作:

string data = "[{\"FirstName\": \"John\", \"LastName\": \"Smith\"}, {\"FirstName\": \"Mohammed\", \"LastName\": \"Lee\"}]"; 
var dt = JsonConvert.DeserializeObject<DataTable>(data);

请注意,整个 json 字符串在 [] 内。即使它是一个只包含一个数组的 json 对象,它也不会工作。

如果您想先反序列化为自定义类型,那么我建议您将完全相同的 json 反序列化为 List&lt;T&gt; 而不是 DataTable。

class Name 
{
    public string FirstName { get; set; }
    public string LastName { get; set; }
}

...

var names = JsonConvert.DeserializeObject<List<Name>>(data);

还有ways to convert the list to a DataTable。话虽如此,一旦您反序列化为自定义列表类型,您还想将其转换为 DataTable 吗?如果要将 DataTable 用于控件上的数据绑定,则还有其他用于绑定源的选项。

【讨论】:

  • 我想把它放到一个数据表中,这样我就可以把它插入到一个 sql server 表中。有更好的方法吗?如果是这样,您可以编辑您的答案吗?
  • 在这种情况下,最好反序列化为您的自定义类型的列表,然后使用table-type input parameter 将所有数据发送到将这些数据插入到 SQL Server 表中的 sproc .
  • 在代码的反序列化行中,我收到错误“无法将当前 JSON 对象反序列化为 List 类型,因为该类型需要 JSON 数组才能正确反序列化。” json也是嵌套的,我已经编辑了问题以显示为json制作的类
  • 哇!如果您有嵌套类型,我认为您不能在那里使用 DataTable。对于您提到的类,您的 json 字符串应该采用这种格式,以便将其反序列化为 List: [{"leaguename":"foo","gameday":1,"ranking":[{"rank ":1,"club":"club1","games":1,"points":1},{"rank":2,"club":"club2","games":2,"points": 2}]},{"leaguename":"bar","gameday":1,"ranking":[{"rank":3,"club":"club3","games":3,"points": 3},{"rank":4,"club":"club4","games":4,"points":4}]}]
  • 我认为它可以放入数据表中,因为我可以通过执行 var myTable = JsonConvert.DeserializeObject(downloadTable); 将数据源分配给反序列化的 json;然后是 GridView1.DataSource = myTable.ranking;。在 Json 中,只有排名部分是一个数组。它看起来像这样: {"league":"topLeague","matchday":5,"ranking":[{"rank":1,"team":"Furies","playedG‌​ames":5,"points ":20},{"rank":1,"team":"Tornado","playedGames":5,"points":15}]}。你知道为什么它不会分解成一个列表吗?
【解决方案2】:

您是否尝试过让您的类继承自 DataTable 类?理想情况下,您将能够操作数据并让最终结果仍然是 DataTable。

【讨论】:

  • 我刚刚尝试过,我不再收到以前使用过的错误,但现在代码在运行时出现错误。在去实化行上,我收到错误“读取 DataTable 时出现意外的 JSON 令牌。预期的 StartArray,得到了 StartObject。'
【解决方案3】:

如果您只有一个对象序列化,则添加方括号以正确解析到数据表。

var json = JsonConvert.SerializeObject(zone, Formatting.None,
                        new JsonSerializerSettings()
                        {
                            ReferenceLoopHandling = ReferenceLoopHandling.Ignore
                        });

json = "[" + json + "]";

DataTable table = JsonConvert.DeserializeObject<DataTable>(json);

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2015-10-26
    • 2020-12-19
    • 2014-06-10
    • 2016-03-04
    • 1970-01-01
    • 2020-12-10
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多