JSONでnullを表す


423

JSONでnull値を返すための推奨メソッドは何ですか?プリミティブの好みは異なりますか?

たとえば、サーバー上のオブジェクトに "myCount"という名前の整数があり、値がない場合、その値の最も適切なJSONは次のようになります。

{}

または

{
    "myCount": null
}

または

{
    "myCount": 0
}

文字列に対する同じ質問-サーバーにnull文字列「myString」がある場合、最高のJSONです。

{}

または

{
    "myString": null
}

または

{
    "myString": ""
}

または(主が私を助けて)

{
    "myString": "null"
}

コレクションがJSONで空のコレクションとして表されるための規約が好きですhttp://jtechies.blogspot.nl/2012/07/item-43-return-empty-arrays-or.html

空の配列が表されます:

{
    "myArray": []
}

要約の編集

「個人的な好み」の議論は現実的であるように見えますが、近視眼的であり、コミュニティーとして、ますます多くの異なるサービス/ソースを消費することになります。JSON構造の規則は、上記のサービスの消費と再利用を正規化するのに役立ちます。標準を確立する限り、いくつかの例外を除いて、ほとんどのジャクソン規約を採用することをお勧めします。

  • オブジェクトはプリミティブよりも優先されます。
  • 空のコレクションはnullよりも優先されます。
  • 値のないオブジェクトはnullとして表されます。
  • プリミティブはその値を返します。

ほとんどがnull値のJSONオブジェクトを返す場合は、複数のサービスにリファクタリングする候補がある可能性があります。

{

    "value1": null,

    "value2": null,

    "text1": null,

    "text2": "hello",

    "intValue": 0, //use primitive only if you are absolutely sure the answer is 0

    "myList": [],

    "myEmptyList": null, //NOT BEST PRACTICE - return [] instead

    "boolean1": null, //use primitive only if you are absolutely sure the answer is true/false

    "littleboolean": false

}

上記のJSONは、次のJavaクラスから生成されました。

package jackson;

import java.util.ArrayList;
import java.util.List;

import com.fasterxml.jackson.databind.ObjectMapper;

public class JacksonApp {

    public static class Data {

        public Integer value1;

        public Integer value2;

        public String text1;

        public String text2 = "hello";

        public int intValue;

        public List<Object> myList = new ArrayList<Object>();

        public List<Object> myEmptyList;

        public Boolean boolean1;

        public boolean littleboolean;

    }

    public static void main(String[] args) throws Exception {
        ObjectMapper mapper = new ObjectMapper();
        System.out.println(mapper.writeValueAsString(new Data()));
    }
}

Mavenの依存関係:

<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-core</artifactId>
    <version>2.3.0</version>
</dependency>

5
最善の方法はありません。具体的なユースケースで、クライアントにとって最も使いやすいものを選択します。ではなく空のコレクションを返すという趣旨でnull、クライアントが空の文字列を使用する方がよいかどうかを検討してください。null「null」という単語を含む文字列は有効な値と区別がつかないので、使用しないでください。
Philipp Reichart、2014年

3
0または空の文字列は、nullとは異なる意味を持つ可能性があり、nullは存在しない属性とは異なる意味を持つ可能性があります。nullを表す場合はnullを使用します。それは最も明白です。
John Sheehan

Objective-CにはNSNull、シングルトンインスタンスを持つ定義済みクラスがあります。そのインスタンスへの参照は、JSONのと同等nullです。他の言語でも同じことができると思います。もちろん、推定されたクラスにキャストする前に、受け取ったオブジェクトのクラスを確認する必要があります。
Hot Licks

2
「null」リストを使用することも、Javaではベストプラクティスではないことに注意してください。リストが空であることが予想される場合は、空のリストに初期化してください。する必要がある場合残る(それが新しいリストで卸売置き換えではなく、値を追加するように修正されるため、例えば)の空、それを初期化し、空のリスト(すなわち)。そうすることで、そうでなければ苦痛になりかねないnull参照バグを回避できます。Collections.emptyList()
Periata Breatta

@HotLicks-Objective-Cが動的に型付けされているためにのみ可能です。たとえば、Javaでは、Null独自のタイプまたはタイプのオブジェクトにのみ値を割り当てることができるため、(有用な)クラスを作成できませんObject
Periata Breatta

回答:


379

それぞれの解析を評価してみましょう:

http://jsfiddle.net/brandonscript/Y2dGv/

var json1 = '{}';
var json2 = '{"myCount": null}';
var json3 = '{"myCount": 0}';
var json4 = '{"myString": ""}';
var json5 = '{"myString": "null"}';
var json6 = '{"myArray": []}';

console.log(JSON.parse(json1)); // {}
console.log(JSON.parse(json2)); // {myCount: null}
console.log(JSON.parse(json3)); // {myCount: 0}
console.log(JSON.parse(json4)); // {myString: ""}
console.log(JSON.parse(json5)); // {myString: "null"}
console.log(JSON.parse(json6)); // {myArray: []}

ここでtl; dr

json2変数のフラグメントは、JSON仕様が表す方法を示していますnull。しかし、いつものように、それはあなたが何をしているのかに依存します-時々それを行うための「正しい」方法は常にあなたの状況でうまくいくとは限りません。あなたの判断を使って、情報に基づいた決定をしてください。


JSON1 {}

空のオブジェクトを返します。そこにデータはありません。あなたが探しているどんなキー(myCountそれでも何かでも)がtypeであることを伝えるだけですundefined


JSON2 {"myCount": null}

この場合、myCountは実際には定義されていますが、その値はnullです。これはない「ではないの両方と同じでundefinedはないnull」、とあなたは一つの条件や他のためにテストされた場合JSON1が失敗するのに対し、これは成功するかもしれません。

これは、JSON仕様nullに従って表現するための決定的な方法です。


JSON3 {"myCount": 0}

この場合、myCountは同じではありません0ですnull、そしてそれは同じではありませんfalse。条件付きステートメントがを評価するmyCount > 0場合、これは価値があるかもしれません。さらに、ここの値に基づいて計算を実行している場合は、0が役立ちます。nullただし、テストする場合は、実際にはまったく機能しません。


JSON4 {"myString": ""}

この場合、空の文字列を取得しています。繰り返しになりますが、JSON2と同様に定義されていますが、空です。あなたは、のためにテストすることができif (obj.myString == "")ますが、あなたがのためにテストができませんでしたnullundefined


JSON5 {"myString": "null"}

文字列値をnullに設定しているので、これはおそらくあなたを困らせるでしょう。この場合は、obj.myString == "null"そうではありません == null


JSON6 {"myArray": []}

これにより、配列はmyArray存在するが、空であることがわかります。これは、でカウントまたは評価を実行する場合に役立ちますmyArray。たとえば、ユーザーが投稿した写真の数を評価したいとしましょう-実行できmyArray.length、それは0:defined を返しますが、投稿された写真はありません。


1
どうもありがとうございました。ほんの小さなサイドノード。Play Json(scala)がシリアル化したときOption [String] = None結果はJSON1ie{}
Neil

207

nullはゼロではありません。それ自体は値ではありません。データの欠落または不明を示す変数のドメイン外の値です。

nullJSONで表現する方法は1つだけです。仕様(RFC 4627およびjson.org)によると:

2.1。価値観

JSON値は、オブジェクト、配列、数値、または文字列、あるいは
次の3つのリテラル名:

  false null tr​​ue

ここに画像の説明を入力してください


8
ヌルが存在しなければならないのはとても残念なことです。4文字で無料。値を完全に除外するだけで良かったでしょう。 json = '{"myValue":}';
リチャードAクワドリング2015

119
@Richard A Quadling-私はHal Abelsonの「プログラムは人々が読むために書かれなければならず、偶然にマシンが実行するためだけに書かれなければならない」のフォロワーです。プログラマーの意図を裏付ける「null」という言葉を好みますが、偶発的な脱落の問題だけではありません。
Scott Smith

13
@Dave May:「JSON値はプログラムではありません」-私のポイントは、明確な方法で意図を伝えることです。はい、4文字余分にかかります。アプリケーションによっては、その違いが大きくなる場合があります。ただし、多くの場合、エラーを間違って見えるようにすることの利点は、マイナーな最適化の利点をはるかに上回ります。
スコットスミス

11
@Daveまた、json.orgによれば、JSONは「人間が読み書きしやすい」とのことです。
Sophivorus

14
また、4つのASCII文字に問題がある場合は、JSONが最善のアプローチではないことに注意してください。バイナリーJSONまたは純粋なバイナリー形式をお勧めします。
PhoneixS

26

表現する方法は1つだけnullです。それはnullです。

console.log(null === null);   // true
console.log(null === true);   // false
console.log(null === false);  // false
console.log(null === 'null'); // false
console.log(null === "null"); // false
console.log(null === "");     // false
console.log(null === []);     // false
console.log(null === 0);      // false

つまり、JSON表現を使用するクライアントのいずれかが===演算子を使用する場合。彼らにとって問題になる可能性があります。

値なし

属性myCountに値がないオブジェクトがあることを伝えたい場合:

{ "myCount": null }

属性なし/属性なし

属性のないオブジェクトがあることを伝える場合はどうなるでしょうか。

{}

クライアントコードはアクセスmyCountして取得しようとしますundefined。それはありません。

空のコレクション

myCount空のリストである属性を持つオブジェクトがあることを伝える場合はどうなるでしょうか。

{ "myCount": [] }

比較による+1の良い例ですが、javascriptとjsonを区別するのに役立ちます。つまり、javascriptでのnullの表現はjsonのnullの表現と一致する必要はありませんでした(ただし一致します)。
Mladen B.

15

nullその特定のキーには値がないことを示すために使用します。たとえばnull、「世帯内のインターネットに接続するデバイスの数」が不明であることを表すために使用します。

一方、{}その特定のキーが適用されない場合に使用します。たとえば、null「インターネットに接続されている車の数」という質問に対して、車を所有していない人に質問があったとしても、カウントを表示しないでください。

そのデフォルトが意味をなさない限り、私は値をデフォルトにしないようにします。を使用nullして値なしを表すことを決定する場合がありますが、確か"null"にそうするために使用しないでください。


7

変数のデータ型(null文字列/オブジェクト、0数値)には「デフォルト」を選択しますが、実際にオブジェクトを消費するコードが期待するコードを確認します。null/ defaultと「存在しない」の間には時々違いがあることを忘れないでください。

nullオブジェクトパターンを確認してください-特別なオブジェクトを渡す代わりにnull(配列や文字列[]nullはなく配列を渡す方がよい場合""があります)。


2

これは個人的な状況選択です。覚えておくべき重要なことは、空の文字列とゼロの数は概念的にとは異なるということですnull

aの場合は、countcount不明または未定義でない限り)常にいくつかの有効な数値が必要ですが、文字列の場合、誰が知っていますか?空の文字列は、アプリケーションで何かを意味する可能性があります。または、そうではないかもしれません。それはあなた次第です。


1

JSON仕様によると、上記のほとんどのコメントで示唆されているように、最も外側のコンテナは辞書(または「オブジェクト」)である必要はありません。リストまたは裸の値(文字列、数値、ブール値、またはnull)にすることもできます。JSONでnull値を表す場合、JSON文字列全体(JSON文字列を含む引用符を除く)は単純nullです。中括弧、括弧、引用符はありません。null値({"key1":null})のキーを含む辞書、またはnull値()のリストを指定できます[null]が、これらはそれ自体がnull値ではなく、適切な辞書およびリストです。同様に、空の辞書({})または空のリスト([])も問題ありませんが、nullでもありません。

Pythonの場合:

>>> print json.loads('{"key1":null}')
{u'key1': None}
>>> print json.loads('[null]')
[None]
>>> print json.loads('[]')
[]
>>> print json.loads('{}')
{}
>>> print json.loads('null')
None

リンクされたJSON仕様ページの右側のサイドバーにあるマッキーマンフォームの文法が、null有効なJSONを構成するという主張を検証することに注意してください。本文とイラストは曖昧であり、オブジェクトと配列のみがルートで有効であることを示唆するものがあると思われる場合。
yoyoyoyosef
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.