1. JSONを思い出そう
JSONはJavaScript Object Notationの略です。名前にJavaScriptと付いていますが、このフォーマットは言語に依存せず、ほとんど(ほとんどね)すべてのプログラミング言語、C#を含めて使えます。データ――オブジェクト、配列、リスト、辞書をテキストで分かりやすく表現するために考案されました。
現代では、ほとんどのプログラムが他のプログラムとやり取りをするので、JSONは事実上の標準になっています。REST APIからユーザー設定の保存、マイクロサービス間の内部通信まで幅広く使われています。理由は明白:人が読める(中括弧が苦手でなければ)、パースが簡単、そしてモダンな言語やライブラリでサポートされているからです。
なぜXMLではないのか?
JSONはXMLよりシンプルで短く、読みやすいです。余計なノイズやタグがなく、ほとんどのプログラミング言語のデータ構造に自然にマッチします。閉じタグや引用符、その他のXML的な面倒事を扱う必要がありません。要するに — JSONは速くて、簡単で、便利です。
2. JSONの基本構文要素
JSONを木構造(またはマトリョーシカ)だと考えてみましょう。オブジェクト、配列、そして原子データで構成されています。使える「ブロック」は次のとおりです:
オブジェクト (Objects)
JSONオブジェクトは中括弧で囲まれた「キー: 値」のペアの集合です { }。
例:
{
"name": "Alice",
"age": 23
}
C#ではこの構造をクラスや辞書で表現できます。
配列 (Arrays)
JSON配列は順序付きの値のリスト(任意の型の値)で、角括弧で囲まれます [ ]。
例:
[1, 2, 3, 42]
あるいは:
[
{"name": "Ivan"},
{"name": "Olga"}
]
C#ではこれはList<T>、T[]や同等のコレクションに対応します。
キーと値のペア
キーは常に文字列(ダブルクォートで囲む)で、値はJSONで許される任意のデータ型になり得ます。
例:
{
"id": 123,
"login": "student",
"isActive": true
}
JSONのデータ型
| JSONの型 | 例 | 説明 |
|---|---|---|
| 数値 (Number) | |
整数または浮動小数点数 |
| 文字列 (String) | |
常にダブルクォートで囲む |
| ブール (Boolean) | |
論理値 |
| null | |
値が存在しないことを示す |
| オブジェクト (Object) | |
辞書やフィールドを持つエンティティ |
| 配列 (Array) | |
値のシーケンス |
例 — 全部まとめると:
{
"id": 1,
"name": "Bob",
"scores": [10, 20, 30],
"profile": {
"email": "bob@mail.com",
"phone": null
},
"isAdmin": false
}
こんなふうに、ユーザーオブジェクトをコンパクトかつ論理的に表現できます。
3. JSONの記述ルール
文字列は常にダブルクォート
シングルクォートにしたくなる気持ちはわかりますが、JSONはそれを許しません。正しい例:
{ "name": "Vera" }
こちらはエラーです:
{ 'name': 'Vera' }
キーは文字列だけ
C#では辞書のキーがintやenumでも構いませんが、JSONではキーは常に文字列です:
{ "2025": "C#の年", "favorite": true }
末尾のコンマは禁止
C#の配列初期化のように余分なコンマを許すケースがあっても、JSONでは閉じ括弧直前の余分なコンマは構文エラーになります!
// エラー!(最後のカンマは許されない)
{
"id": 10,
"name": "Oleg",
}
正しい書き方:
{
"id": 10,
"name": "Oleg"
}
スペースと改行
見やすさのために入れて構いません。パーサーは無視します。人間向けにはpretty-printed(整形済み)JSON、ネット送信用にはminified(1行・空白無し)JSONを使うことが多いです。
4. C#オブジェクトがJSONにどう変換されるか
System.Text.Json.JsonSerializer.Serialize()でオブジェクトをシリアライズすると、オブジェクトのフィールドやプロパティが「キー: 値」のペアになります。
C#クラスとシリアライズの例
public class Book
{
public string Title { get; set; }
public int Pages { get; set; }
}
var book = new Book { Title = "CLR via C#", Pages = 900 };
string json = JsonSerializer.Serialize(book);
Console.WriteLine(json); // {"Title":"CLR via C#","Pages":900}
コレクション
- List<int> は [1,2,3] に変換される
- string[] は ["hi", "wow"] に変換される
- List<Person> はオブジェクトの配列になる
辞書(Dictionary)
Dictionary<string, int> のような辞書はオブジェクトに変換されます:
var dict = new Dictionary<string, int>
{
["apples"] = 5, ["bananas"] = 10
};
string json = JsonSerializer.Serialize(dict);
// {"apples":5,"bananas":10}
5. ビジュアル図:JSONの構造
ネストはマトリョーシカみたい
オブジェクト
│
├── ペア: "name": "Alex"
├── ペア: "hobbies": 配列
│ │
│ ├── "skiing"
│ └── "programming"
└── ペア: "profile": オブジェクト
│
├── "age": 42
└── "city": "バーゼル"
結果は:
{
"name": "Alex",
"hobbies": ["skiing", "programming"],
"profile": {
"age": 42,
"city": "バーゼル"
}
}
6. よくあるエラーと構文の注意点
プログラミングに完璧な世界はありません—JSONにも落とし穴があります。間違った引用符、余分なカンマ、キーをクォートし忘れるなどでパーサーはエラーを投げます。
もう一つの「罠」は先頭にゼロが付いた数値です。JSONではこれは禁止されています(例えば、0123 はエラー)。
覚えておくと便利: 一部のパーサー(例えばJavaScriptのJSON.parse)は寛容で小さな違反を許すことがあります。しかし、多くの厳格なパーサー(C#/.NETのものなど)はほんの少しの構文違反でもエラーにします。
7. C#のデータをJSONに変換する例
複雑な構造をシリアライズしてみましょう。学習用アプリを想定して、学生のリストをJSONファイルに保存するとします。
クラスを定義:
public class Student
{
public string Name { get; set; }
public int Age { get; set; }
}
リストにデータを入れる:
var students = new List<Student>
{
new Student { Name = "アンナ", Age = 20 },
new Student { Name = "ニキータ", Age = 22 }
};
シリアライズ:
using System.Text.Json;
// 学生のリストをJSON文字列にシリアライズする
string json = JsonSerializer.Serialize(students, new JsonSerializerOptions { WriteIndented = true });
Console.WriteLine(json);
/*
[
{
"Name": "アンナ",
"Age": 20
},
{
"Name": "ニキータ",
"Age": 22
}
]
*/
ほら、便利でしょ?各学生はJSON配列の中の個別のオブジェクトになっています。
8. ミニジェネレータ:手でJSONを書く方法
テストデータを手で書く必要があることがあります。チェックリスト:
- オブジェクトなら外側は中括弧、配列なら外側は角括弧。
- キーは常にダブルクォートで囲まれた文字列。
- 値は文字列(ダブルクォート)、数値、true、false、null、オブジェクト({})、配列([])のいずれか。
- 要素の間はカンマで区切るが、最後の要素の後には付けない!
- インデントやスペースは可読性のために使う(必須ではない)。
GO TO FULL VERSION