2013-03-19 5 views
6

私はJson.NETでJSON構造を処理しようといくつかの問題に遭遇しています:JSONは無名の配列が含まれている場合Json.NET:JSON配列をデシリアライズ

私のクラスでは動作しません。

JSON例:Json.NETため

{ 
    "graph_property" : [{ 
      "name" : "calculation_method", 
      "value" : "Arithmetic" 
     }, { 
      "name" : "graph_type", 
      "value" : "TIME" 
     } 
    ], 
    "measurement" : [{ 
      "id" : "9997666", 
      "alias" : "Measurement (TxP)[IE]-Home Page - Total Time (seconds)", 
      "bucket_data" : [{ 
        "name" : "2013-MAR-18 12:00 AM", 
        "id" : 1, 
        "perf_data" : { 
         "value" : "2.244", 
         "unit" : "seconds" 
        }, 
        "avail_data" : { 
         "value" : "99.67", 
         "unit" : "percent" 
        }, 
        "data_count" : { 
         "value" : "299", 
         "unit" : "#" 
        } 
       } 
      ], 
      "graph_option" : [{ 
        "name" : "perfwarning", 
        "value" : "-", 
        "unit" : "seconds" 
       }, { 
        "name" : "perfcritical", 
        "value" : "-", 
        "unit" : "seconds" 
       }, { 
        "name" : "availwarning", 
        "value" : "-", 
        "unit" : "percent" 
       }, { 
        "name" : "availcritical", 
        "value" : "-", 
        "unit" : "percent" 
       }, { 
        "name" : "bucketsize", 
        "value" : "86400", 
        "unit" : "seconds" 
       }, { 
        "name" : "rows", 
        "value" : "1", 
        "unit" : "#" 
       }, { 
        "name" : "pagecomponent", 
        "value" : "Total Time", 
        "unit" : "seconds" 
       }, { 
        "name" : "avg_perf", 
        "value" : "2.244", 
        "unit" : "seconds" 
       }, { 
        "name" : "avg_avail", 
        "value" : "99.67", 
        "unit" : "percent" 
       }, { 
        "name" : "total_datapoint_count", 
        "value" : "300", 
        "unit" : "#" 
       }, {} 

      ] 
     }, { 
      "id" : "9997666", 
      "alias" : "Measurement (TxP)[IE]-Women - Total Time (seconds)", 
      "bucket_data" : [{ 
        "name" : "2013-MAR-18 12:00 AM", 
        "id" : 1, 
        "perf_data" : { 
         "value" : "0.979", 
         "unit" : "seconds" 
        }, 
        "avail_data" : { 
         "value" : "100.00", 
         "unit" : "percent" 
        }, 
        "data_count" : { 
         "value" : "299", 
         "unit" : "#" 
        } 
       } 
      ], 
      "graph_option" : [{ 
        "name" : "perfwarning", 
        "value" : "-", 
        "unit" : "seconds" 
       }, { 
        "name" : "perfcritical", 
        "value" : "-", 
        "unit" : "seconds" 
       }, { 
        "name" : "availwarning", 
        "value" : "-", 
        "unit" : "percent" 
       }, { 
        "name" : "availcritical", 
        "value" : "-", 
        "unit" : "percent" 
       }, { 
        "name" : "bucketsize", 
        "value" : "86400", 
        "unit" : "seconds" 
       }, { 
        "name" : "rows", 
        "value" : "1", 
        "unit" : "#" 
       }, { 
        "name" : "pagecomponent", 
        "value" : "Total Time", 
        "unit" : "seconds" 
       }, { 
        "name" : "avg_perf", 
        "value" : "0.979", 
        "unit" : "seconds" 
       }, { 
        "name" : "avg_avail", 
        "value" : "100.00", 
        "unit" : "percent" 
       }, { 
        "name" : "total_datapoint_count", 
        "value" : "299", 
        "unit" : "#" 
       }, {} 

      ] 
     } 
    ], 
    "link" : { 
     "type" : "application/json", 
     "href" : "http://api.website.tld?format=json", 
     "rel" : "slotmetadata" 
    } 
} 

クラス:

using System; 
using System.Collections.Generic; 

namespace CAKR.Graph 
{ 
    /// <summary> 
    /// Description of KN_Graph. 
    /// </summary> 
    public class GraphProperty 
    { 
     public string name { get; set; } 
     public string value { get; set; } 
    } 

    public class PerfData 
    { 
     public string value { get; set; } 
     public string unit { get; set; } 
    } 

    public class AvailData 
    { 
     public string value { get; set; } 
     public string unit { get; set; } 
    } 

    public class DataCount 
    { 
     public string value { get; set; } 
     public string unit { get; set; } 
    } 

    public class BucketData 
    { 
     public string name { get; set; } 
     public int id { get; set; } 
     public PerfData perf_data { get; set; } 
     public AvailData avail_data { get; set; } 
     public DataCount data_count { get; set; } 
    } 

    public class GraphOption 
    { 
     public string name { get; set; } 
     public string value { get; set; } 
     public string unit { get; set; } 
    } 

    public class Measurement 
    { 
     public string id { get; set; } 
     public string alias { get; set; } 
     public List<BucketData> bucket_data { get; set; } 
     public List<GraphOption> graph_option { get; set; } 
    } 

    public class Link 
    { 
     public string type { get; set; } 
     public string href { get; set; } 
     public string rel { get; set; } 
    } 

    public class RootObject 
    { 
     public List<GraphProperty> graph_property { get; set; } 
     public List<Measurement> measurement { get; set; } 
     public Link link { get; set; } 
    } 
} 

マイコード:

var myObject = JsonConvert.DeserializeObject<CAKR.Graph.Measurement>(MyJsonString); 

私はありませんSなぜ私は "Measurment"の子配列のデータを含むオブジェクトを取得しないのですか? 名前付きの値を挿入すると、それは機能します...

+0

は、あなたのJSONは、[JSONリント](HTTP有効であるかないかどうかを検証するために、将来的に使用するための良いリンクです。 – MethodMan

+0

'Class'に対して' namespace'ではなく 'CAKR.Graph.Measurement'がクラスではないはずです。 – MethodMan

+0

[JSON配列を型に変換できません--Json.NET](http: //stackoverflow.com/questions/9452901/cannot-deserialize-json-array-into-type-json-net) – MethodMan

答えて

4

あなたはほとんどあります。ただ、

var myObject = JsonConvert.DeserializeObject<CAKR.Graph.RootObject>(MyJsonString); 

代わりに、すべての

var myObject = JsonConvert.DeserializeObject<CAKR.Graph.Measurement>(MyJsonString); 
+0

。しかし、測定オブジェクトは何らかの理由で "NULL"のままです。 – t313

2

まずの使用、あなたが本当に彼らはMyJsonStringに提示されているとおりにMeasurementクラスのすべてのプロパティの名前を指定する必要はありません。 JsonProperty属性を使用して、クラスプロパティを飾ることができます。 。あなたは、あなたが(あなたのケースで、それはだIEnumerable<Measurement>

次のコードは役立つはずDeserialize方法の正しいTの種類を提供する必要があり、あなたのMyJsonStringの一部をデシリアライズし、Measurementの配列のみを抽出したい場合は

もう一つは、次のとおりです。

dynamic context = JObject.Parse(MyJsonString); 
    var myObject = JsonConvert.DeserializeObject<IEnumerable<Measurement>>(context.measurement.ToString()); 
+0

おかげJevgenij!これは本当に何かに私を得た。 – t313

+0

ようこそ。 –

8

だから私はこの作業を取得するにはかなりの時間のために苦しんでいた。しかし、最終的に解決策はそれほど難しいことではありません。うまくいけば、私の応答で、私は何人かの人々を助けるが。

私の場合はソリューションは、

  1. が配列の配列の中に、などなど、あなたのJSONオブジェクトは、オブジェクトのフォーマットが正しいことを確認してください
  2. をnu.get使用してプロジェクトにJSON.netをインストールしました!例は...

{ "ProductDetail":[json2csharp.comへ

{ 
     "ProjectImg" : "http://placehold.it/400x300", 
     "Category"  : "Cars", 
     "ProjectTitle" : "Cars of the future", 
     "ProjectDesc" : "Test project", 
     "GenSpecList" : ["Specs1", "Specs2", "Specs3", "Specs4"], 
     "OptionList" : [{ "OptionNr" : "1", 
           "Options" : ["Opt1", "Opt2", "Opt3"] 
          }, 
          { "OptionNr" : "2", 
           "Options" : ["Opt1", "Opt2", "Opt3"] 
          }, 
          { "OptionNr" : "3", 
           "Options" : ["Opt1", "Opt2", "Opt3"] 
          }, 
          { "OptionNr" : "4", 
           "Options" : ["Opt1", "Opt2", "Opt3"] 
          }, 
          { "OptionNr" : "5", 
           "Options" : ["Opt1", "Opt2", "Opt3"] 
          }, 
          { "OptionNr" : "6", 
           "Options" : ["Opt1", "Opt2", "Opt3"] 
          } 
         ], 
     "Articles"  : [{ "tileImg" : "'Images/Project/1.jpg'", 
           "tileTit" : "Title1", 
           "tileArt" : "Article text here..." 
          }, 
          { 
           "tileImg" : "'Images/Project/2.jpg'", 
           "tileTit" : "Title2", 
           "tileArt" : "Article text here..." 
          }, 
          { 
           "tileImg" : "'Images/Project/3.jpg'", 
           "tileTit" : "Title3", 
           "tileArt" : "Article text here..." 
          }, 
          { 
           "tileImg" : "'Images/Project/4.jpg'", 
           "tileTit" : "Title4", 
           "tileArt" : "Article text here..." 
          } 
         ] 
    } 
] 
} 
  1. 行くとは、入力ボックスにあなたのJSONオブジェクトをコピーして、生成ボタンをクリックします。あなたのViewModelに生成されたcsharpモデルをコピーします(これは実際に私の苦労を解決する鍵でした!)。
  2. 私の場合、json2csharpによって生成されたすべてのクラスのプライマリクラスです。comが

    using Project.Details; //<-- this is my ViewModel namespace name 
    using Newtonsoft.Json; 
    using System.IO; 
    using System.Threading.Tasks; 
    
    namespace WebApplication.Controllers 
    { 
        public class JSONController : Controller 
        { 
         // 
         // GET: /JSON/ 
         public async Task<ActionResult> Index() 
         { 
          StreamReader file = new StreamReader("C:\\Users\\YourName\\etc\\File.json"); 
          String json = await file.ReadToEndAsync(); 
    
          var Project = JsonConvert.DeserializeObject<RootObject>(json); 
    
          return View(); 
         } 
        } 
    } 
    

(ちょうどここに完全なファイルをコピーした)RootObjectした後、コントローラに次のコードを使用するよう

public class Article 
{ 
    public string tileImg { get; set; } 
    public string tileTit { get; set; } 
    public string tileArt { get; set; } 
} 

public class OptionList 
{ 
    public string OptionNr { get; set; } 
    public List<string> Options { get; set; } 
} 

public class ProductDetail 
{ 
    public string ProjectImg { get; set; } 
    public string Category { get; set; } 
    public string ProjectTitle { get; set; } 
    public string ProjectDesc { get; set; } 
    public List<string> GenSpecList { get; set; } 
    public List<OptionList> OptionList { get; set; } 
    public List<Article> Articles { get; set; } 
} 

public class RootObject 
{ 
    public List<ProductDetail> ProductDetail { get; set; } 
} 
  • の下に見えた今、すべてがうまく、配列の中に動作するはずですあなたは私の解決策が役に立ったと評価して、アレイのなど 希望は、...私はefficencyで物事を逃す場合、私はこのコードを改善するために、あなたからいくつかのヒントを受け取ることを望むので、私はダイハードプログラマではないよ注意

    よろしくお願いします。 Raymond

  • +0

    私はKEY値と値を取得したい...それはそれを行うのですか?ありがとう – Si8

    0

    私は非常に簡単な方法を使ってJson Arraysを逆直列化します。多数の公開変数を持つ公開クラスのトンを使用する代わりに。私は、動的オブジェクトを使用してJSONConvert.DeserializeObjectにオブジェクトとしてJSONを渡します。

    これは、それがどのように動作するかです。

    string json = { 'Name': 'John Doe', 
        'Address': { 'City': 'Atlanta', 'State': 'GA' }, 
        'Age': 30} 
    

    JSONConvert.DeserializeObjectに文字列jsonを渡すことができます。

    dynamic outputArray = JsonConvert.DeserializeObject(json); 
    

    次に、作成したダイナミックアイテムを使用して、Jsonデータを収集することができます。

    string getName = outputArray.Name //This will return "John Doe" 
    

    あなたがJSON内の配列を持っている場合は、あなたがまだ保存することができます

    string getCity = outputArray.Address.City; //This will return "Atlanta". 
    

    それはパブリック変数のクラスターを持たずに、あなたがからデータを取得場所を変更することは非常に簡単です...使用することができます必要に応じて値をパブリック変数に変換します。

    次は、私は完全なメソッドを使用する方法です:// jsonlint:ここ

    using (var client = new WebClient()) 
         { 
          string json = client.DownloadString(url); 
          string output = json.ToString(); 
    
          dynamic outputArray = JsonConvert.DeserializeObject(output); 
    
          string _age = outputArray.age; 
          string appID = outputArray.data.app_id; 
    
          Debug.Write(outputArray.Something); //Just match value of json   
         } 
    
    +0

    jsonが配列ではなく、ただオブジェクト –

    関連する問題