キーと値のペアに使用するJSON構造は何ですか?


23

キーと値のペアに適したJSON形式は何ですか?その理由は何ですか?

[{"key1": "value1"}, {"key2": "value2"}]

または:

[{"Name": "key1", "Value": "value1"}, {"Name": "key2", "Value": "value2"}]

または:

{"key1": "value1", "key2": "value2"}

最初のバリアントは、よりコンパクトで、より「意味的に意味のある」ようです。2番目のバリアントは、より均等に構造化されているように見えるため、処理に役立ちます。3番目の亜種はさらに意味がありそうです。

キーと値のペアは、他のアイテムに任意のデータを添付するために使用されます。データをJSONとしてシリアル化して、システムを介してデータをラウンドチップする必要があります。


3
注文が必要でない限り、考慮しないのはなぜ{"key1": "value1", "key2": "value2"}ですか?
ケニー

4
JSONはすでに(ネスト可能な)辞書です。
ケイシースピークマン

1
あなたの問題は、これらの形式のいずれかが機能するという説明が十分に広いことであり、本当の問題は、クライアントがどのテクノロジーを使用するかに応じて、どのように消費を簡単にするかです。
scriptin

ニーズを満たす最も単純なものを使用する必要があります。できれば、それが単純なオブジェクト形式(#3)になります。ただし、さらに多くのオプションを探している場合は、2つの配列を同時に使用できます。1つはキー用、もう1つは値用です。オブジェクトキーと重複キー(#3ではサポートされません)を引き続きサポートしながら、可能な限りコンパクトになります。
エリックエイド

回答:


10

最初のオプションを選択するか、3番目のオプションを選択するかは、ユースケースによって異なります。同じタイプの多くの異なるインスタンスをモデリングする場合は、最初のものを選択してください。たとえば、人のリストがあります。1つのものの多くの異なる属性をモデリングする場合は、3番目のものを選択します。最初の形式ではキーを繰り返し使用できますが、3番目の形式では使用できません。

2番目のオプションはひどいもので、適切なユースケースをまだ見つけていません。ひどいのは、より冗長であることに加えて、単一レベルのJSONの場合、ほとんどのライブラリの辞書/マップへの自動変換が中断されるためです。深くネストされたJSONの場合、XPathに似たクエリインターフェイスが破損します。

これにより、作業が面倒になります。また、コンパイル時にキーがわからない場合は、辞書またはXPathインターフェイスが必要になります。クラスに変換できないためです。今では大したことではないように思えるかもしれませんが、データ形式が長くなればなるほど、変更が難しくなります。


5
2番目のオプションの大きな利点は、非文字列キー、特に複合キーで機能することです。
-CodesInChaos

1
2番目のオプションはひどいもので、ユースケースをまだ見つけていませんか?多くのキー/値ペアを持つ辞書の配列は、複数のオブジェクトを送信するための最も一般的な形式である必要があります。
gnasher729

2
@ gnasher729、「最も一般的な形式」の場合、実際のキーはすべて左側にあります [{"key1": "value1", "key2": "value2"}]。ここでの2番目の形式は、実際のキーを右側に配置し、「名前」という別のキーを使用して実際のキーを指すため、標準ツールで解析するのが非常に難しくなります。
カールビーレフェルト

@CodesInChaosを紹介します。ただし、それでも非常に特殊なケースでなければなりません。野生でそれが必要だとは思っていません。
カールビーレフェルト

3
申し訳ありませんが、これは悪い答えです。2番目のオプションは非常に一般的に使用され、推奨されています。キーの柔軟性を可能にし、コンシューマを壊すことなく拡張(より多くの値/メタデータフィールドを使用)できるようにし、要素の順序を保持できます。さらに、与えられた理由は偽です。「自動変換」を壊さず(作成者のプレゼンテーションを配列として尊重するだけです)、XPathのようなクエリインターフェイスで正常に動作します。唯一の欠点は、冗長性の増加です。
ヘジャズマン

5

一般に、3番目の形式が最適です。ただし、ここに、1番目の形式に適したものの例を示します。

[{
  "username": "foo",
  "id": 1
}, {
  "username": "bar",
  "id": 2
}, {
  "username": "baz",
  "id": 3
}]

ここで、各オブジェクトは個別のものを参照します(各オブジェクトは他のオブジェクトと同じキーを使用するため、マージできません)。ただし、リスト内の各オブジェクトは、1)短く、2)ユーザー名とIDを持つ1つのものではなく、ユーザー名とIDを持つ1つのものを参照するためと{ "username": "foo", "id": 1 }いうよりも、むしろ保存され[{ "username": "foo" }, { "id": 1 }]ます。

2番目のオプションの問題は、JSONとしても動作するようにも非常に冗長になることです。ただし、プロパティに関するメタ情報を保存する必要がある場合は使用できます。例:

{
  "key": "foo",
  "value": 1,
  "mutable": true
}

ここmutableでは、親オブジェクトではなくプロパティ自体を変更できるかどうかの仮想的なケースを参照します。このようなメタObject.defineProperty情報は、プロパティに関する「構成可能」、「列挙可能」、および「書き込み可能」な情報を保存するJavaScriptに似ています。


私はC#RESTエンドポイントに送信していたJSONの最初のフォーマットを使用しようとしていましたが、辞書オブジェクトに変換していませんでした。それを3番目の形式に変換すると、それは解消されました。
fizch

5

これらはキー/値のペアだと言います。その場合は、#3:キー/値ペアの辞書を使用します。

これらがキー/値のペアではない場合、「キー」および「値」と呼ばず、任意のコンテンツを持つ辞書の配列である#2を使用します。

構造#1は、キーと値のペアだけでなくその順序も必要でない限り、ただの動きです。あなたはめったにそれをしません。


3

jsonを受け取った人の靴に自分を入れてください。キー名がわからない場合、最初または最後の形式でキー名を取得するにはどうすればよいですか?もちろん、jsonをループすることもできますが、3つの形式すべてが同じ結果を達成するため、構文の問題にすぎません。これが唯一の意味のある質問だと思います。キー名がわかっている場合、最初または最後のオプションはよりコンパクトですが、そうでない場合は2番目の選択肢がより理解しやすいです。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.