JSON の配列で string, number, true/false, null, array, object など異種の要素が混ざったものを、デシリアライザに Newtonsoft.Json および System.Text.Json を使って .NET のオブジェクトに変換するとどうなるかを書きます。
上の画像の前者 result1.Data が Newtonsoft.Json を使った結果、後者 result2.Data が System.Text.Json を使った結果です。
Data は両方とも object[] 型で、その各要素も object 型ですが、その中身が違うところに注目してください。それがこの記事で書きたかったことです。
この例ほど多種の要素が混じっている配列というケースは実際にはないかもしれませんが、"NaN" という文字列と number ぐらいならあるかもしれません。なので、違いを覚えておくと役に立つかもしれないと思って備忘録として残しておくことにしました。
上の画像を表示するのに具体的のどのようにしたかを以下に書いておきます。
まず、元になる JSON 文字列ですが、以下の通りです。
{
"Header": {
"Id": 10,
"Name": "Test Data"
},
"Data": [
"NaN",
-0.010565,
true,
10,
1.02e2,
null,
[ "abc", "def", "ghi" ],
{ "Object": "test" }
]
}
Visual Studio の機能を使って上の JSON 文字列から C# のクラス定義を生成すると以下のようになります。やり方は先の記事「JSON 文字列から C# のクラス定義生成」を見てください。
public class Rootobject
{
public Header Header { get; set; }
public object[] Data { get; set; }
}
public class Header
{
public int Id { get; set; }
public string Name { get; set; }
}
"Data" は object[] 型にデシリアライズするという点に注目してください。
Newtonsoft.Json および System.Text.Json を使って JSON 文字列を上の C# のオブジェクトにデシリアライズします。コードは以下の通りです。ターゲットフレームワーク .NET 7.0 のコンソールアプリを使いました。
string filepath = @"C:\Users\...\json1.json";
string jsonString = "";
using (StreamReader sr = File.OpenText(filepath))
{
jsonString = sr.ReadToEnd();
}
// Newtonsoft.Json
var result1 = Newtonsoft.Json.JsonConvert
.DeserializeObject<Rootobject>(jsonString);
// System.Text.Json
var result2 = System.Text.Json.JsonSerializer
.Deserialize<Rootobject>(jsonString);
上のコードを Visual Studio 2022 でデバッグ実行し、ブレークポイントで止めて変数 result1 と result2 の中身を表示したのがこの記事の一番上の画像です。