Jaka jest preferowana metoda zwracania wartości zerowych w JSON? Czy istnieje inna preferencja dla prymitywów?
Na przykład, jeśli mój obiekt na serwerze ma liczbę całkowitą o nazwie „myCount” bez wartości, najbardziej poprawnym JSON dla tej wartości byłoby:
{}
lub
{
"myCount": null
}
lub
{
"myCount": 0
}
To samo pytanie dla ciągów - jeśli mam ciąg zerowy „myString” na serwerze, to najlepszy JSON:
{}
lub
{
"myString": null
}
lub
{
"myString": ""
}
lub (Panie, pomóż mi)
{
"myString": "null"
}
Podoba mi się konwencja reprezentowania kolekcji w JSON jako pusta kolekcja http://jtechies.blogspot.nl/2012/07/item-43-return-empty-arrays-or.html
Pusta tablica byłaby reprezentowana:
{
"myArray": []
}
Podsumowanie edycji
Argument „osobistych preferencji” wydaje się realistyczny, ale w skrócie, jako społeczność będziemy konsumować coraz większą liczbę różnych usług / źródeł. Konwencje dotyczące struktury JSON pomogłyby znormalizować zużycie i ponowne wykorzystanie tych usług. Jeśli chodzi o ustanowienie standardu, proponuję przyjęcie większości konwencji Jacksona z kilkoma wyjątkami:
- Przedmioty są lepsze od prymitywów.
- Puste kolekcje są preferowane niż puste.
- Obiekty bez wartości są reprezentowane jako null.
- Prymitywy zwracają swoją wartość.
Jeśli zwracasz obiekt JSON z przeważnie wartościami zerowymi, możesz mieć kandydata do refaktoryzacji do wielu usług.
{
"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
}
Powyższy JSON został wygenerowany z następującej klasy 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()));
}
}
Zależność od Maven:
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-core</artifactId>
<version>2.3.0</version>
</dependency>
null
, zastanów się, czy lepiej jest dla twojego klienta z pustym ciągiem lubnull
- ciąg zawierający słowo „null” jest nie do odróżnienia od prawidłowej wartości, nie rób tego.NSNull
klasa, która ma instancję singleton. Odwołanie do tego wystąpienia jest równoważne odwołaniu JSONnull
. Domyślam się, że inny język mógłby zrobić to samo. Oczywiście należałoby sprawdzić klasę otrzymanego obiektu przed rzutem na przypuszczalną klasę - być „zerowym świadomym”, jak to było.Collections.emptyList()
.). Pozwala to uniknąć błędów zerowych odniesień, które w innym przypadku mogą być uciążliwe.Null
klasy, ponieważ można przypisać jej wartości tylko do obiektów własnego typu lub typuObject
.Odpowiedzi:
Oceńmy parsowanie każdego z nich:
http://jsfiddle.net/brandonscript/Y2dGv/
JSON1
{}
Zwraca pusty obiekt. Nie ma tam żadnych danych, a tylko powie ci, że każdy klucz, którego szukasz (czy to
myCount
coś innego) jest typuundefined
.JSON2
{"myCount": null}
W tym przypadku
myCount
jest faktycznie zdefiniowany, chociaż jego wartość tonull
. To nie jest to samo co „nieundefined
i nienull
”, a jeśli testujesz dla jednego lub drugiego warunku, może się to udać, podczas gdy JSON1 zawiedzie.Jest to ostateczny sposób reprezentacji
null
zgodnie ze specyfikacją JSON .JSON3
{"myCount": 0}
W tym przypadku myCount wynosi 0. To nie to samo co
null
i to nie to samo cofalse
. Jeśli twoje zdanie warunkowe oceniamyCount > 0
, to warto je mieć. Ponadto, jeśli wykonujesz obliczenia na podstawie wartości tutaj, 0 może być przydatne. Jeśli jednak próbujesz przetestowaćnull
, w rzeczywistości to nie zadziała.JSON4
{"myString": ""}
W takim przypadku otrzymujesz pusty ciąg. Ponownie, podobnie jak w JSON2, jest zdefiniowane, ale jest puste. Możesz przetestować,
if (obj.myString == "")
ale nie możesz przetestowaćnull
lubundefined
.JSON5
{"myString": "null"}
To prawdopodobnie wpędzi cię w kłopoty, ponieważ ustawiasz wartość ciągu na null; w tym przypadku
obj.myString == "null"
jednak tak nie jest== null
.JSON6
{"myArray": []}
To powie ci, że twoja tablica
myArray
istnieje, ale jest pusta. Jest to przydatne, jeśli próbujesz wykonać policzenie lub ocenęmyArray
. Powiedzmy na przykład, że chcesz ocenić liczbę zdjęć opublikowanych przez użytkownika - możesz to zrobićmyArray.length
i zwróci0
: zdefiniowane, ale nie opublikowano żadnych zdjęć.źródło
JSON1
np.{}
null
nie jest zero. Nie jest to wartość sama w sobie : jest to wartość poza domeną zmiennej wskazująca na brakujące lub nieznane dane.Jest tylko jeden sposób reprezentacji
null
w JSON. Zgodnie ze specyfikacjami ( RFC 4627 i json.org ):źródło
json = '{"myValue":}';
Jest tylko jeden sposób reprezentacji
null
; to jest znull
.To jest do powiedzenia; jeśli którykolwiek z klientów korzystających z reprezentacji JSON korzysta z
===
operatora; to może być dla nich problem.bez wartości
Jeśli chcesz przekazać, że masz obiekt, którego atrybut
myCount
nie ma wartości:brak atrybutu / brak atrybutu
Co jeśli chcesz przekazać, że masz obiekt bez atrybutów:
Kod klienta będzie próbował uzyskać dostęp
myCount
i uzyskaćundefined
; nie ma go.pusta kolekcja
Co jeśli chcesz przekazać, że masz obiekt z atrybutem,
myCount
który jest pustą listą:źródło
Chciałbym użyć,
null
aby pokazać, że nie ma wartości dla tego konkretnego klucza. Na przykład użyjnull
do przedstawienia, że „liczba urządzeń w twoim domu łączy się z Internetem” jest nieznana.Z drugiej strony użyj,
{}
jeśli ten konkretny klucz nie ma zastosowania. Na przykład nie powinieneś pokazywać liczby, nawet jeślinull
na pytanie „liczba samochodów z aktywnym połączeniem internetowym” jest zadawane osobie, która nie jest właścicielem żadnego samochodu.Unikałbym domyślnej wartości, chyba że ma to sens. Chociaż możesz zdecydować się na użycie,
null
aby nie przedstawiać żadnej wartości, na pewno nigdy tego nie używaj"null"
.źródło
Wybrałbym „default” dla typu danych zmiennej (
null
dla łańcuchów / obiektów,0
dla liczb), ale rzeczywiście sprawdzam, jakiego kodu oczekuje obiekt. Nie zapominaj, że czasami istnieje różnica międzynull
/ default a „not present”.Sprawdź wzorzec obiektu zerowego - czasem lepiej jest przekazać jakiś obiekt specjalny zamiast
null
(tj.[]
Tablicę zamiastnull
tablic lub""
łańcuchów).źródło
Jest to osobisty i sytuacyjny wybór. Ważną rzeczą do zapamiętania jest to, że pusty ciąg i liczba zero są koncepcyjnie różne
null
.W przypadku
count
pewnie zawsze potrzebujesz poprawnego numeru (chyba żecount
jest nieznany lub niezdefiniowany), ale w przypadku ciągów, kto wie? Pusty ciąg może oznaczać coś w twojej aplikacji. A może nie. Ty decydujesz.źródło
Zgodnie ze specyfikacją JSON najbardziej zewnętrzny pojemnik nie musi być słownikiem (lub „obiektem”), jak sugeruje większość powyższych komentarzy. Może to być także lista lub sama wartość (tj. Ciąg, liczba, wartość logiczna lub null). Jeśli chcesz reprezentować wartość zerową w JSON, cały ciąg JSON (z wyłączeniem cudzysłowów zawierających ciąg JSON) jest po prostu
null
. Bez nawiasów klamrowych, bez nawiasów, bez cudzysłowów. Możesz podać słownik zawierający klucz o wartości null ({"key1":null}
) lub listę o wartości null ([null]
), ale same nie są to wartości null - są to właściwe słowniki i listy. Podobnie, pusty słownik ({}
) lub pusta lista ([]
) są w porządku, ale też nie są zerowe.W Pythonie:
źródło
null
stanowi prawidłowy JSON. Główny tekst i ilustracje są niejednoznaczne i jeśli coś wydaje się sugerować, że tylko obiekty i tablice są prawidłowe u podstawy.