So analysieren Sie JSON in Java


1049

Ich habe den folgenden JSON-Text. Wie kann ich es analysieren, um die Werte von zu erhalten?pageName , pagePic, post_idetc.?

{
   "pageInfo": {
         "pageName": "abc",
         "pagePic": "http://example.com/content.jpg"
    },
    "posts": [
         {
              "post_id": "123456789012_123456789012",
              "actor_id": "1234567890",
              "picOfPersonWhoPosted": "http://example.com/photo.jpg",
              "nameOfPersonWhoPosted": "Jane Doe",
              "message": "Sounds cool. Can't wait to see it!",
              "likesCount": "2",
              "comments": [],
              "timeOfPost": "1234567890"
         }
    ]
}

7
In Java integrierte JSON-Bibliotheken sind der schnelle Weg, dies zu tun, aber meiner Erfahrung nach ist GSON die beste Bibliothek, um einen JSON schmerzlos in ein POJO zu analysieren.
Iman Akbari

16
Dies ist die erste hoch
gewählte

6
@ JaysonMinard stimmte zu. Nach Mod-Intervention gefragt. Dies sollte wirklich geschlossen werden. Ich nahm anfangs (fälschlicherweise) an, dass ich dies nicht tun konnte, während die Frage geschützt war, also habe ich sie ungeschützt und mein Ding gemacht. Schützen Sie es jetzt erneut, um Antworten mit geringen Wiederholungszahlen und dergleichen zu verhindern, während Sie auf einen Mod warten.
Mena

4
"Diese Frage zeigt keinen Forschungsaufwand" - Tooltip für Downvote-Schaltflächen
Jean-François Corbett

6
Diese Frage wird auf Meta diskutiert .
Mark Amery

Antworten:


753

Die org.json- Bibliothek ist einfach zu bedienen. Beispielcode unten:

import org.json.*;

String jsonString = ... ; //assign your JSON String here
JSONObject obj = new JSONObject(jsonString);
String pageName = obj.getJSONObject("pageInfo").getString("pageName");

JSONArray arr = obj.getJSONArray("posts");
for (int i = 0; i < arr.length(); i++)
{
    String post_id = arr.getJSONObject(i).getString("post_id");
    ......
}

Weitere Beispiele finden Sie unter: JSON in Java analysieren

Herunterladbare JAR: http://mvnrepository.com/artifact/org.json/json


15
Ich stimme @StaxMan zu. Ich habe gerade org.json ausprobiert und es ist schrecklich umständlich. Es spielt zum Beispiel wirklich nicht mit Standard-Java-Sammlungstypen.
Ken Williams

7
@StaxMan Ich würde org.jsonandere Bibliotheken für einfaches JSON-Parsing auswählen, ohne auch nur hinzuschauen . Es ist die Referenzbibliothek, die Douglas Crockford (der JSON-Entdecker) erstellt hat.
Omar Al-Ithawi

31
@OmarIthawi das ist einfach albern. Es ist ein Proof-of-Concept mit umständlicher API und ineffizienter Implementierung. Ich denke, es ist besser, Bibliotheken nach ihren eigenen Vorzügen zu betrachten, als zu versuchen, die Qualität aus der Sichtbarkeit der Autoren abzuleiten - Doug hat viele Dinge erreicht, aber das ändert nicht wirklich die Eigenschaften der jeweiligen Bibliothek. Vor 10 Jahren war es das einzige Spiel in der Stadt, aber seitdem wurden viele positive Fortschritte erzielt. Es ist wie Struts of Json Libs.
StaxMan

12
org.json gehört zu den schlechtesten json-Bibliotheken. Vor der Auswahl sollten Sie sich den Funktionsumfang und die Leistung der verfügbaren JSON-Bibliotheken ansehen. Hier ist ein Benchmark I Jackson hat den Vergleich, Gson, org.json, GENSON JMH mit: github.com/fabienrenaud/java-json-benchmark . Jackson ist hier der klare Gewinner.
Fabien

4
Die Lizenz enthält keine häufig verwendeten Open Source-Lizenzen und besitzt auch Urheberrechte.
Christian Vielma

536

Nehmen wir für das Beispiel an, Sie haben eine Klasse Personmit nur a name.

private class Person {
    public String name;

    public Person(String name) {
        this.name = name;
    }
}

Google GSON ( Maven )

Mein persönlicher Favorit in Bezug auf die großartige JSON-Serialisierung / De-Serialisierung von Objekten.

Gson g = new Gson();

Person person = g.fromJson("{\"name\": \"John\"}", Person.class);
System.out.println(person.name); //John

System.out.println(g.toJson(person)); // {"name":"John"}

Aktualisieren

Wenn Sie ein einzelnes Attribut herausholen möchten, können Sie dies auch problemlos mit der Google-Bibliothek tun:

JsonObject jsonObject = new JsonParser().parse("{\"name\": \"John\"}").getAsJsonObject();

System.out.println(jsonObject.get("name").getAsString()); //John

Org.JSON ( Maven )

Wenn Sie keine Objekt-De-Serialisierung benötigen, sondern nur ein Attribut erhalten möchten, können Sie org.json ausprobieren ( oder das obige GSON-Beispiel betrachten! ).

JSONObject obj = new JSONObject("{\"name\": \"John\"}");

System.out.println(obj.getString("name")); //John

Jackson ( Maven )

ObjectMapper mapper = new ObjectMapper();
Person user = mapper.readValue("{\"name\": \"John\"}", Person.class);

System.out.println(user.name); //John

16
Gute Antwort. Ein Vorschlag für eine geringfügige Verbesserung: Sowohl GSON als auch Jackson unterstützen auch die Verwendung der JSON-Baumdarstellung (für Jackson sind dies JsonNodes, GSON hat etwas Ähnliches). Könnte gut sein, um Schnipsel zu zeigen, da dies der einzigen Möglichkeit ähnelt, die org.json bietet.
StaxMan

Zwei weitere erwähnenswerte Bibliotheken (der Vollständigkeit
halber

3
@NeWarge, warum? Es scheint mir, dass diese Antwort davon ausgeht, dass man bereits eine Java-Klasse definiert hat, die genau die gleichen Felder wie die JSON-Zeichenfolge enthält, nicht weniger und nicht mehr. Dies ist eine ziemlich starke Annahme.
Andrea Lazzarotto

1
json-simple und oracles jsonp bieten eine hervorragende Leistung: github.com/fabienrenaud/java-json-benchmark Wählen Sie für die Leistung jackson oder dsljson.
Fabien

GSON unterstützt keine dynamische Filterung von Feldern auf anderen Ebenen als root!
Gangnus

102
  1. Wenn Sie ein Java-Objekt aus JSON erstellen möchten und umgekehrt, verwenden Sie GSON- oder JACKSON-Jars von Drittanbietern usw.

    //from object to JSON 
    Gson gson = new Gson();
    gson.toJson(yourObject);
    
    // from JSON to object 
    yourObject o = gson.fromJson(JSONString,yourObject.class);
  2. Wenn Sie jedoch nur eine JSON-Zeichenfolge analysieren und einige Werte abrufen möchten (ODER eine JSON-Zeichenfolge von Grund auf neu erstellen möchten, um sie über Kabel zu senden), verwenden Sie einfach das JaveEE-JAR, das JsonReader, JsonArray, JsonObject usw. enthält. Möglicherweise möchten Sie die Implementierung davon herunterladen Spezifikation wie javax.json. Mit diesen beiden Gläsern kann ich den JSON analysieren und die Werte verwenden.

    Diese APIs folgen tatsächlich dem DOM / SAX-Parsing-Modell von XML.

    Response response = request.get(); // REST call 
        JsonReader jsonReader = Json.createReader(new StringReader(response.readEntity(String.class)));
        JsonArray jsonArray = jsonReader.readArray();
        ListIterator l = jsonArray.listIterator();
        while ( l.hasNext() ) {
              JsonObject j = (JsonObject)l.next();
              JsonObject ciAttr = j.getJsonObject("ciAttributes");

4
@nondescript Wenn ich raten müsste, würde ich sagen, dass es abgelehnt wurde, weil es die Frage des Originalplakats nicht beantwortet: "Was ist der erforderliche Code?" Die Antworten, die positiv bewertet wurden, lieferten Codefragmente.
jewbix.cube

4
Hinweis: Jackson und GSON unterstützen beide die Bindung im Baumstil und / oder in Maps / Lists, sodass kein Java EE-Paket (javax.json) verwendet werden muss. javax.json hat außer Jackson oder GSON wenig zu bieten.
StaxMan

Ich schlage vor, einen Link zur JavaEE-Bibliothek hinzuzufügen.
Basil Bourque

72

Quick-JSON-Parser ist sehr einfach, flexibel, sehr schnell und anpassbar. Versuch es

Eigenschaften:

  • Entspricht der JSON-Spezifikation (RFC4627)
  • Hochleistungs-JSON-Parser
  • Unterstützt den flexiblen / konfigurierbaren Parsing-Ansatz
  • Konfigurierbare Validierung von Schlüssel / Wert-Paaren einer beliebigen JSON-Hierarchie
  • Einfach zu bedienen # Sehr kleiner Platzbedarf
  • Löst entwicklerfreundliche und leicht nachvollziehbare Ausnahmen aus
  • Unterstützung für steckbare benutzerdefinierte Validierungen - Schlüssel / Werte können validiert werden, indem benutzerdefinierte Validatoren konfiguriert werden, sobald sie auftreten
  • Parser-Unterstützung validieren und nicht validieren
  • Unterstützung für zwei Konfigurationstypen (JSON / XML) zur Verwendung des Quick-JSON-Validierungsparsers
  • Benötigt JDK 1.5
  • Keine Abhängigkeit von externen Bibliotheken
  • Unterstützung für die JSON-Generierung durch Objektserialisierung
  • Unterstützung für die Auswahl des Sammlungstyps während des Analyseprozesses

Es kann folgendermaßen verwendet werden:

JsonParserFactory factory=JsonParserFactory.getInstance();
JSONParser parser=factory.newJsonParser();
Map jsonMap=parser.parseJson(jsonString);

3
Gibt es einen Javadoc?
Jboi

24
Dieses Paket kann beim Parsen keine leeren Werte verarbeiten. Zum Beispiel: ... "description": "" ... löst eine Ausnahme aus
Ivan

6
Ich habe dieses Problem (und viele andere) in code.google.com/p/quick-json/issues/detail?id=11 behoben. Ich hoffe, der Autor wird sich die Zeit nehmen, um es in der offiziellen Version zu beheben.
Noamik

8
Von den aufgeführten Funktionen ist nichts im Vergleich zu anderen Optionen einzigartig - und der Anspruch auf hohe Leistung wird von nichts unterstützt. Im Gegensatz zu ausgereifteren Bibliotheken (Gson, Jackson, Genson, Boon), die in Benchmarks wie github.com/eishay/jvm-serializers , github.com/novoj/JavaJsonPerformanceTest oder developer.com/lang/jscript/… - I enthalten sind Ich habe nicht gesehen, dass diese Bibliothek in Tests enthalten ist oder dass sie weit verbreitet ist.
StaxMan

26
Dieses Projekt scheint tot zu sein und scheint nicht mehr im zentralen Maven-Repository gehostet zu sein.
8bitjunkie

40

Sie könnten Google Gson verwenden .

Mit dieser Bibliothek müssen Sie nur ein Modell mit derselben JSON-Struktur erstellen. Dann wird das Modell automatisch ausgefüllt. Sie müssen Ihre Variablen als JSON-Schlüssel aufrufen oder verwenden, @SerializedNamewenn Sie andere Namen verwenden möchten.

JSON

Aus Ihrem Beispiel:

{
    "pageInfo": {
        "pageName": "abc",
        "pagePic": "http://example.com/content.jpg"
    }
    "posts": [
        {
            "post_id": "123456789012_123456789012",
            "actor_id": "1234567890",
            "picOfPersonWhoPosted": "http://example.com/photo.jpg",
            "nameOfPersonWhoPosted": "Jane Doe",
            "message": "Sounds cool. Can't wait to see it!",
            "likesCount": "2",
            "comments": [],
            "timeOfPost": "1234567890"
        }
    ]
}

Modell

class MyModel {

    private PageInfo pageInfo;
    private ArrayList<Post> posts = new ArrayList<>();
}

class PageInfo {

    private String pageName;
    private String pagePic;
}

class Post {

    private String post_id;

    @SerializedName("actor_id") // <- example SerializedName
    private String actorId;

    private String picOfPersonWhoPosted;
    private String nameOfPersonWhoPosted;
    private String message;
    private String likesCount;
    private ArrayList<String> comments;
    private String timeOfPost;
}

Parsing

Jetzt können Sie mit der Gson-Bibliothek analysieren:

MyModel model = gson.fromJson(jsonString, MyModel.class);

Gradle-Import

Denken Sie daran, die Bibliothek in die Gradle-Datei der App zu importieren

implementation 'com.google.code.gson:gson:2.8.6' // or earlier versions

Automatische Modellgenerierung

Sie können Modell generieren von JSON automatisch Online - Tools wie mit dieser .


38

Fast alle Antworten erfordern eine vollständige Deserialisierung des JSON in ein Java-Objekt, bevor auf den Wert in der interessierenden Eigenschaft zugegriffen werden kann. Eine andere Alternative, die diesen Weg nicht geht, ist die Verwendung von JsonPATH, das XPath für JSON ähnelt und das Durchlaufen von JSON-Objekten ermöglicht.

Es ist eine Spezifikation und die guten Leute von JayWay haben eine Java-Implementierung für die Spezifikation erstellt, die Sie hier finden: https://github.com/jayway/JsonPath

Um es zu verwenden, fügen Sie es Ihrem Projekt hinzu, z. B.:

<dependency>
    <groupId>com.jayway.jsonpath</groupId>
    <artifactId>json-path</artifactId>
    <version>${version}</version>
</dependency>

und zu verwenden:

String pageName = JsonPath.read(yourJsonString, "$.pageInfo.pageName");
String pagePic = JsonPath.read(yourJsonString, "$.pageInfo.pagePic");
String post_id = JsonPath.read(yourJsonString, "$.pagePosts[0].post_id");

usw...

Weitere Informationen zu den anderen Möglichkeiten zum Überqueren von JSON finden Sie auf der JsonPath-Spezifikationsseite.


Dies ist eine sehr gute Bibliothek, insbesondere zum Lesen und Aktualisieren von JSON, aber Vorsicht vor bekannten Problemen mit dieser Bibliothek. Siehe [1]: github.com/json-path/JsonPath/issues/272 [2]: github.com/json-path/JsonPath/issues/375
Papigee

38

A - Erklärung

Sie können Jackson- Bibliotheken verwenden, um JSON-Zeichenfolgen in POJO- Instanzen ( Plain Old Java Object ) zu binden . POJO ist einfach eine Klasse mit nur privaten Feldern und öffentlichen Getter / Setter-Methoden. Jackson wird die Methoden durchlaufen (mithilfe von Reflection ) und das JSON-Objekt der POJO-Instanz zuordnen, wenn die Feldnamen der Klasse zu den Feldnamen des JSON-Objekts passen.

In Ihrem JSON-Objekt, das eigentlich ein zusammengesetztes Objekt ist, besteht das Hauptobjekt aus zwei Unterobjekten. Unsere POJO-Klassen sollten also dieselbe Hierarchie haben. Ich werde das gesamte JSON-Objekt als Page- Objekt aufrufen . Das Seitenobjekt besteht aus einem PageInfo- Objekt und einem Beitrag Objektarray.

Wir müssen also drei verschiedene POJO-Klassen erstellen.

  • Page Class, eine Zusammenstellung aus PageInfo Class und Array von Post - Instanzen
  • Seiteninfo Klasse
  • Beiträge Klasse

Das einzige Paket, das ich verwendet habe, ist Jackson ObjectMapper. Wir binden Daten.

com.fasterxml.jackson.databind.ObjectMapper

Die erforderlichen Abhängigkeiten, die JAR-Dateien, sind unten aufgeführt;

  • jackson-core-2.5.1.jar
  • jackson-database-2.5.1.jar
  • jackson-annotations-2.5.0.jar

Hier ist der erforderliche Code;

B - Hauptklasse POJO: Seite

package com.levo.jsonex.model;

public class Page {

    private PageInfo pageInfo;
    private Post[] posts;

    public PageInfo getPageInfo() {
        return pageInfo;
    }

    public void setPageInfo(PageInfo pageInfo) {
        this.pageInfo = pageInfo;
    }

    public Post[] getPosts() {
        return posts;
    }

    public void setPosts(Post[] posts) {
        this.posts = posts;
    }

}

C - Kind POJO Klasse: PageInfo

package com.levo.jsonex.model;

public class PageInfo {

    private String pageName;
    private String pagePic;

    public String getPageName() {
        return pageName;
    }

    public void setPageName(String pageName) {
        this.pageName = pageName;
    }

    public String getPagePic() {
        return pagePic;
    }

    public void setPagePic(String pagePic) {
        this.pagePic = pagePic;
    }

}

D - Kind POJO Klasse: Post

package com.levo.jsonex.model;

public class Post {

    private String post_id;
    private String actor_id;
    private String picOfPersonWhoPosted;
    private String nameOfPersonWhoPosted;
    private String message;
    private int likesCount;
    private String[] comments;
    private int timeOfPost;

    public String getPost_id() {
        return post_id;
    }

    public void setPost_id(String post_id) {
        this.post_id = post_id;
    }

    public String getActor_id() {
        return actor_id;
    }

    public void setActor_id(String actor_id) {
        this.actor_id = actor_id;
    }

    public String getPicOfPersonWhoPosted() {
        return picOfPersonWhoPosted;
    }

    public void setPicOfPersonWhoPosted(String picOfPersonWhoPosted) {
        this.picOfPersonWhoPosted = picOfPersonWhoPosted;
    }

    public String getNameOfPersonWhoPosted() {
        return nameOfPersonWhoPosted;
    }

    public void setNameOfPersonWhoPosted(String nameOfPersonWhoPosted) {
        this.nameOfPersonWhoPosted = nameOfPersonWhoPosted;
    }

    public String getMessage() {
        return message;
    }

    public void setMessage(String message) {
        this.message = message;
    }

    public int getLikesCount() {
        return likesCount;
    }

    public void setLikesCount(int likesCount) {
        this.likesCount = likesCount;
    }

    public String[] getComments() {
        return comments;
    }

    public void setComments(String[] comments) {
        this.comments = comments;
    }

    public int getTimeOfPost() {
        return timeOfPost;
    }

    public void setTimeOfPost(int timeOfPost) {
        this.timeOfPost = timeOfPost;
    }

}

E - Beispiel-JSON-Datei: sampleJSONFile.json

Ich habe gerade Ihr JSON-Beispiel in diese Datei kopiert und unter den Projektordner gelegt.

{
   "pageInfo": {
         "pageName": "abc",
         "pagePic": "http://example.com/content.jpg"
    },
    "posts": [
         {
              "post_id": "123456789012_123456789012",
              "actor_id": "1234567890",
              "picOfPersonWhoPosted": "http://example.com/photo.jpg",
              "nameOfPersonWhoPosted": "Jane Doe",
              "message": "Sounds cool. Can't wait to see it!",
              "likesCount": "2",
              "comments": [],
              "timeOfPost": "1234567890"
         }
    ]
}

F - Demo-Code

package com.levo.jsonex;

import java.io.File;
import java.io.IOException;
import java.util.Arrays;

import com.fasterxml.jackson.databind.ObjectMapper;
import com.levo.jsonex.model.Page;
import com.levo.jsonex.model.PageInfo;
import com.levo.jsonex.model.Post;

public class JSONDemo {

    public static void main(String[] args) {
        ObjectMapper objectMapper = new ObjectMapper();

        try {
            Page page = objectMapper.readValue(new File("sampleJSONFile.json"), Page.class);

            printParsedObject(page);
        } catch (IOException e) {
            e.printStackTrace();
        }

    }

    private static void printParsedObject(Page page) {
        printPageInfo(page.getPageInfo());
        System.out.println();
        printPosts(page.getPosts());
    }

    private static void printPageInfo(PageInfo pageInfo) {
        System.out.println("Page Info;");
        System.out.println("**********");
        System.out.println("\tPage Name : " + pageInfo.getPageName());
        System.out.println("\tPage Pic  : " + pageInfo.getPagePic());
    }

    private static void printPosts(Post[] posts) {
        System.out.println("Page Posts;");
        System.out.println("**********");
        for(Post post : posts) {
            printPost(post);
        }
    }

    private static void printPost(Post post) {
        System.out.println("\tPost Id                   : " + post.getPost_id());
        System.out.println("\tActor Id                  : " + post.getActor_id());
        System.out.println("\tPic Of Person Who Posted  : " + post.getPicOfPersonWhoPosted());
        System.out.println("\tName Of Person Who Posted : " + post.getNameOfPersonWhoPosted());
        System.out.println("\tMessage                   : " + post.getMessage());
        System.out.println("\tLikes Count               : " + post.getLikesCount());
        System.out.println("\tComments                  : " + Arrays.toString(post.getComments()));
        System.out.println("\tTime Of Post              : " + post.getTimeOfPost());
    }

}

G - Demo-Ausgabe

Page Info;
****(*****
    Page Name : abc
    Page Pic  : http://example.com/content.jpg
Page Posts;
**********
    Post Id                   : 123456789012_123456789012
    Actor Id                  : 1234567890
    Pic Of Person Who Posted  : http://example.com/photo.jpg
    Name Of Person Who Posted : Jane Doe
    Message                   : Sounds cool. Can't wait to see it!
    Likes Count               : 2
    Comments                  : []
    Time Of Post              : 1234567890

26

Verwenden Sie minimal-json, das sehr schnell und einfach zu bedienen ist. Sie können aus String obj und Stream analysieren.

Beispieldaten:

{
  "order": 4711,
  "items": [
    {
      "name": "NE555 Timer IC",
      "cat-id": "645723",
      "quantity": 10,
    },
    {
      "name": "LM358N OpAmp IC",
      "cat-id": "764525",
      "quantity": 2
    }
  ]
}

Parsing:

JsonObject object = Json.parse(input).asObject();
int orders = object.get("order").asInt();
JsonArray items = object.get("items").asArray();

JSON erstellen:

JsonObject user = Json.object().add("name", "Sakib").add("age", 23);

Maven:

<dependency>
  <groupId>com.eclipsesource.minimal-json</groupId>
  <artifactId>minimal-json</artifactId>
  <version>0.9.4</version>
</dependency>

Wie wird das Pojo aussehen?
Jesse

Verwenden Sie für Pojo gson. Diese Bibliothek wird nicht unterstützt.
Sakib Sami

22

Ich glaube, die beste Vorgehensweise sollte darin bestehen, die offizielle Java JSON-API zu verwenden, die noch in Arbeit ist.


7
Seit ich geantwortet habe, habe ich angefangen, Jackson zu verwenden, und ich denke, es ist eine der besten Bibliotheken für die JSON-De-Serialisierung.
Giovanni Botta

2
Warum verwenden sie JSONP wieder, um etwas anderes als JSON mit Padding zu bedeuten ? ...
Chris Wesseling

@ ChrisWesseling Was meinst du?
Giovanni Botta

"Java-API für die JSON-Verarbeitung (JSON-P)" ist der Titel des Dokuments, auf das Sie verlinken. Und es verwirrte mich, weil ich wusste, dass JSONP etwas anderes bedeutet.
Chris Wesseling

1
@ ChrisWesseling oh das ist verwirrend. Das haben sie für die Spezifikation gewählt. Wie gesagt, ich würde direkt nach Jackson gehen.
Giovanni Botta

22

Da es noch niemand erwähnt hat, ist hier ein Anfang einer Lösung mit Nashorn (JavaScript-Laufzeitteil von Java 8, aber in Java 11 veraltet).

Lösung

private static final String EXTRACTOR_SCRIPT =
    "var fun = function(raw) { " +
    "var json = JSON.parse(raw); " +
    "return [json.pageInfo.pageName, json.pageInfo.pagePic, json.posts[0].post_id];};";

public void run() throws ScriptException, NoSuchMethodException {
    ScriptEngine engine = new ScriptEngineManager().getEngineByName("nashorn");
    engine.eval(EXTRACTOR_SCRIPT);
    Invocable invocable = (Invocable) engine;
    JSObject result = (JSObject) invocable.invokeFunction("fun", JSON);
    result.values().forEach(e -> System.out.println(e));
}

Leistungsvergleich

Ich habe JSON-Inhalte geschrieben, die drei Arrays mit jeweils 20, 20 und 100 Elementen enthalten. Ich möchte nur die 100 Elemente aus dem dritten Array erhalten. Ich verwende die folgende JavaScript-Funktion, um meine Einträge zu analysieren und abzurufen.

var fun = function(raw) {JSON.parse(raw).entries};

Das millionenfache Ausführen des Anrufs mit Nashorn dauert 7,5 bis 7,8 Sekunden

(JSObject) invocable.invokeFunction("fun", json);

org.json dauert 20 ~ 21 Sekunden

new JSONObject(JSON).getJSONArray("entries");

Jackson braucht 6,5 ~ 7 Sekunden

mapper.readValue(JSON, Entries.class).getEntries();

In diesem Fall schneidet Jackson besser ab als Nashorn, was viel besser abschneidet als org.json. Die Nashorn-API ist schwieriger zu verwenden als die von org.json oder Jackson. Abhängig von Ihren Anforderungen können Jackson und Nashorn beide praktikable Lösungen sein.


1
Was ist die Einheit " ""? Nicht Zoll? Ist es Sekunden? Protokoll?
Peter Mortensen

1
@PeterMortensen bedeutet Sekunden. Da es unklar erscheint, werde ich es ändern. Danke für die Bewertung.
otonglet

2
Leider ist Nashorn in Java 11 veraltet. JEP 335 .
Per Mildner

1
Ich weiß, dass Nashorn veraltet ist, aber diese Antwort hat mir gefallen, weil ich keine Abhängigkeiten wollte. Allerdings musste ich das Beispiel ein wenig ScriptEngine engine = new ScriptEngineManager().getEngineByName("JavaScript"); engine.eval("var fun = function(raw) { return JSON.parse(raw); };"); Map<String, Object> json = (Map<String, Object>) ((Invocable) engine).invokeFunction("fun", jsonString);
überarbeiten

21

Das folgende Beispiel zeigt, wie der Text in der Frage gelesen wird, der als "jsonText" -Variable dargestellt wird. Diese Lösung verwendet die Java EE7- API javax.json (die in einigen anderen Antworten erwähnt wird). Der Grund, warum ich es als separate Antwort hinzugefügt habe, ist, dass der folgende Code zeigt, wie auf einige der in der Frage angezeigten Werte tatsächlich zugegriffen werden kann. Eine Implementierung der javax.json-API wäre erforderlich, damit dieser Code ausgeführt wird. Das vollständige Paket für jede der erforderlichen Klassen war enthalten, da ich keine "import" -Anweisungen deklarieren wollte.

javax.json.JsonReader jr = 
    javax.json.Json.createReader(new StringReader(jsonText));
javax.json.JsonObject jo = jr.readObject();

//Read the page info.
javax.json.JsonObject pageInfo = jo.getJsonObject("pageInfo");
System.out.println(pageInfo.getString("pageName"));

//Read the posts.
javax.json.JsonArray posts = jo.getJsonArray("posts");
//Read the first post.
javax.json.JsonObject post = posts.getJsonObject(0);
//Read the post_id field.
String postId = post.getString("post_id");

Bevor jemand diese Antwort ablehnt, weil sie nicht GSON, org.json, Jackson oder eines der anderen verfügbaren Frameworks von Drittanbietern verwendet, ist dies ein Beispiel für "erforderlichen Code" pro Frage, um den bereitgestellten Text zu analysieren. Mir ist klar, dass die Einhaltung des aktuellen Standards JSR 353 für JDK 9 nicht berücksichtigt wurde. Daher sollte die JSR 353-Spezifikation genauso behandelt werden wie jede andere JSON-Handhabungsimplementierung von Drittanbietern.


15

Das hat mich umgehauen, wie einfach es war. Sie können einfach ein StringHalten Ihres JSON an den Konstruktor eines JSONObject im Standardpaket org.json übergeben.

JSONArray rootOfPage =  new JSONArray(JSONString);

Erledigt. Lässt das Mikrofon fallen . Dies funktioniert auch mit JSONObjects. Danach können Sie einfach Ihre Hierarchie der ObjectsVerwendung der get()Methoden für Ihre Objekte durchsehen.


13
Der JSONArrayTyp ist nicht Teil der J2SE JDK-API, und Sie sagen nicht, welche API oder Drittanbieter-Bibliothek diesen Typ bereitstellt.
Bobulous

2
Nicht, dass ich es empfehlen würde, aber ich denke, dies bezieht sich auf das "org.json" -Paket von json.org/java . Früher wurde es verwendet, bevor gute Java-Bibliotheken verfügbar wurden, aber dies war vor Jahren (2008 oder früher)
StaxMan

1
Oder bedeutet brainmurphy1 JSONArray in Android?
Alexander Farber

12

In Java sind viele JSON-Bibliotheken verfügbar.

Die bekanntesten sind: Jackson, GSON, Genson, FastJson und org.json.

Es gibt normalerweise drei Dinge, die man bei der Auswahl einer Bibliothek beachten sollte:

  1. Performance
  2. Benutzerfreundlichkeit (Code ist einfach zu schreiben und lesbar) - das gehört zu den Funktionen.
  3. Für mobile Apps: Abhängigkeit / JAR-Größe

Speziell für JSON-Bibliotheken (und alle Serialisierungs- / Deserialisierungsbibliotheken) ist die Datenbindung normalerweise auch von Interesse, da das Schreiben von Boiler-Plate-Code zum Packen / Entpacken der Daten nicht mehr erforderlich ist.

Für 1 siehe diesen Benchmark: https://github.com/fabienrenaud/java-json-benchmark Ich habe JMH verwendet, das die Leistung von Serialisierern und Deserialisierern unter Verwendung von Stream (jackson, gson, genson, fastjson, org.json, jsonp) vergleicht und Datenbindungs-APIs. Für 2 finden Sie zahlreiche Beispiele im Internet. Der obige Benchmark kann auch als Quelle für Beispiele verwendet werden ...

Schnelles Herausnehmen des Benchmarks: Jackson schneidet fünf- bis sechsmal besser ab als org.json und mehr als zweimal besser als GSON.

Für Ihr spezielles Beispiel dekodiert der folgende Code Ihren JSON mit Jackson:

public class MyObj {

    private PageInfo pageInfo;
    private List<Post> posts;

    static final class PageInfo {
        private String pageName;
        private String pagePic;
    }

    static final class Post {
        private String post_id;
        @JsonProperty("actor_id");
        private String actorId;
        @JsonProperty("picOfPersonWhoPosted")
        private String pictureOfPoster;
        @JsonProperty("nameOfPersonWhoPosted")
        private String nameOfPoster;
        private String likesCount;
        private List<String> comments;
        private String timeOfPost;
    }

    private static final ObjectMapper JACKSON = new ObjectMapper();
    public static void main(String[] args) throws IOException {
        MyObj o = JACKSON.readValue(args[0], MyObj.class); // assumes args[0] contains your json payload provided in your question.
    }
}

Lassen Sie mich wissen, wenn Sie Fragen haben.


11

Zusätzlich zu anderen Antworten empfehle ich diesen Online- OpenSource- Dienst jsonschema2pojo.org zum schnellen Generieren von Java-Klassen aus json oder json schema für GSON, Jackson 1.x oder Jackson 2.x. Zum Beispiel, wenn Sie haben:

{
   "pageInfo": {
         "pageName": "abc",
         "pagePic": "http://example.com/content.jpg"
    }
    "posts": [
         {
              "post_id": "123456789012_123456789012",
              "actor_id": 1234567890,
              "picOfPersonWhoPosted": "http://example.com/photo.jpg",
              "nameOfPersonWhoPosted": "Jane Doe",
              "message": "Sounds cool. Can't wait to see it!",
              "likesCount": 2,
              "comments": [],
              "timeOfPost": 1234567890
         }
    ]
}

Das jsonschema2pojo.org für GSON generiert:

@Generated("org.jsonschema2pojo")
public class Container {
    @SerializedName("pageInfo")
    @Expose
    public PageInfo pageInfo;
    @SerializedName("posts")
    @Expose
    public List<Post> posts = new ArrayList<Post>();
}

@Generated("org.jsonschema2pojo")
public class PageInfo {
    @SerializedName("pageName")
    @Expose
    public String pageName;
    @SerializedName("pagePic")
    @Expose
    public String pagePic;
}

@Generated("org.jsonschema2pojo")
public class Post {
    @SerializedName("post_id")
    @Expose
    public String postId;
    @SerializedName("actor_id")
    @Expose
    public long actorId;
    @SerializedName("picOfPersonWhoPosted")
    @Expose
    public String picOfPersonWhoPosted;
    @SerializedName("nameOfPersonWhoPosted")
    @Expose
    public String nameOfPersonWhoPosted;
    @SerializedName("message")
    @Expose
    public String message;
    @SerializedName("likesCount")
    @Expose
    public long likesCount;
    @SerializedName("comments")
    @Expose
    public List<Object> comments = new ArrayList<Object>();
    @SerializedName("timeOfPost")
    @Expose
    public long timeOfPost;
}

9

Wenn Sie eine Java-Klasse (z. B. Nachricht) haben, die die JSON-Zeichenfolge (jsonString) darstellt, können Sie die Jackson JSON-Bibliothek verwenden mit:

Message message= new ObjectMapper().readValue(jsonString, Message.class);

und vom Nachrichtenobjekt können Sie jedes seiner Attribute abrufen.


9

Gson ist leicht zu erlernen und zu implementieren. Was wir wissen müssen, sind zwei Methoden

  • toJson () - Konvertiert das Java-Objekt in das JSON-Format

  • fromJson () - Konvertiert JSON in ein Java-Objekt

`

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import com.google.gson.Gson;

public class GsonExample {
    public static void main(String[] args) {

    Gson gson = new Gson();

    try {

        BufferedReader br = new BufferedReader(
            new FileReader("c:\\file.json"));

        //convert the json string back to object
        DataObject obj = gson.fromJson(br, DataObject.class);

        System.out.println(obj);

    } catch (IOException e) {
        e.printStackTrace();
    }

    }
}

`


Vollständige Informationen zu Gson finden Sie unter den folgenden Links. github.com/google/gson/blob/master/UserGuide.md
venkat

9

Es sind viele Open Source-Bibliotheken vorhanden, um JSON-Inhalte auf ein Objekt zu analysieren oder nur JSON-Werte zu lesen. Sie müssen lediglich Werte lesen und in ein benutzerdefiniertes Objekt analysieren. Die org.json-Bibliothek reicht also in Ihrem Fall aus.

Verwenden Sie die Bibliothek org.json, um sie zu analysieren und JsonObject zu erstellen:

JSONObject jsonObj = new JSONObject(<jsonStr>);

Verwenden Sie nun dieses Objekt, um Ihre Werte abzurufen:

String id = jsonObj.getString("pageInfo");

Ein vollständiges Beispiel finden Sie hier:

So analysieren Sie JSON in Java


Anscheinend enthalten alle Ihre Antworten einen Link zu dieser Site. Wenn es sich um Spam handelt, hören Sie bitte auf. Wenn nicht, entschuldigen Sie die Verwirrung, aber ich denke nicht, dass es notwendig ist, in all Ihren Antworten einen Link zu posten.
Donald Duck

1
Es ist schwierig, eine Antwort zu geben, in der Sie alle Szenarien erklären können. Wie in diesem Fall, wie man ein JSON-Array oder mehrere JSON-Objekte liest. Selbst wenn ich dies tue, wäre die Antwort sehr lang und die Person könnte verwirrt werden. Also gebe ich einen Link, wo die richtige Erklärung gegeben wird, mit dem richtigen Beispiel. Er kann sich für einen Besuch entscheiden oder nur meine Erklärung verwenden.
Lalitbhagtani

1
Es scheint mir, dass der von Ihnen bereitgestellte Link nur das Lesen von JSON zeigt. Wo finde ich auch Informationen zu JSON?
Lampros Tzanetos

Entschuldigung, aber ich habe Ihre Frage nicht verstanden: - "Wie man auch JSON macht"
lalitbhagtani

7

Bitte machen Sie so etwas:

JSONParser jsonParser = new JSONParser();
JSONObject obj = (JSONObject) jsonParser.parse(contentString);
String product = (String) jsonObject.get("productId");

10
Äh, welche Bibliothek ist das?
Stewart

2
Ich denke, er benutzt org.json.simple
Lasitha Yapa

7

Sie können die Gson-Bibliothek verwenden, um die JSON-Zeichenfolge zu analysieren.

Gson gson = new Gson();
JsonObject jsonObject = gson.fromJson(jsonAsString, JsonObject.class);

String pageName = jsonObject.getAsJsonObject("pageInfo").get("pageName").getAsString();
String pagePic = jsonObject.getAsJsonObject("pageInfo").get("pagePic").getAsString();
String postId = jsonObject.getAsJsonArray("posts").get(0).getAsJsonObject().get("post_id").getAsString();

Sie können das Array "posts" auch folgendermaßen durchlaufen:

JsonArray posts = jsonObject.getAsJsonArray("posts");
for (JsonElement post : posts) {
  String postId = post.getAsJsonObject().get("post_id").getAsString();
  //do something
}

5
{
   "pageInfo": {
         "pageName": "abc",
         "pagePic": "http://example.com/content.jpg"
    },
    "posts": [
         {
              "post_id": "123456789012_123456789012",
              "actor_id": "1234567890",
              "picOfPersonWhoPosted": "http://example.com/photo.jpg",
              "nameOfPersonWhoPosted": "Jane Doe",
              "message": "Sounds cool. Can't wait to see it!",
              "likesCount": "2",
              "comments": [],
              "timeOfPost": "1234567890"
         }
    ]
}

Java code :

JSONObject obj = new JSONObject(responsejsonobj);
String pageName = obj.getJSONObject("pageInfo").getString("pageName");

JSONArray arr = obj.getJSONArray("posts");
for (int i = 0; i < arr.length(); i++)
{
    String post_id = arr.getJSONObject(i).getString("post_id");
    ......etc
}

9
Bitte erläutern Sie Ihre Antwort, da Nur-Code-Antworten anderen weit weniger als gut dokumentierten Code helfen. Siehe "Gib einem Mann einen Fisch und du fütterst ihn einen Tag lang; lehre einen Mann das Fischen und du fütterst ihn ein Leben lang" .
Wai Ha Lee

Es wäre gut zu erwähnen, dass dies für 'org.json' lib ist. Ich denke jedoch nicht, dass dies eine gute Möglichkeit ist, dies zu tun, da es sehr ausführlich ist und die 'org.json'-Bibliothek selbst veraltet ist (langsame, umständliche API). Es gibt bessere Möglichkeiten: GSON, Jackson, Boon, Genson.
StaxMan

5

Lesen Sie den folgenden Blog-Beitrag, JSON in Java .

Dieser Beitrag ist ein bisschen alt, aber ich möchte trotzdem Ihre Frage beantworten.

Schritt 1: Erstellen Sie eine POJO-Klasse Ihrer Daten.

Schritt 2: Erstellen Sie nun ein Objekt mit JSON.

Employee employee = null;
ObjectMapper mapper = new ObjectMapper();
try{
    employee =  mapper.readValue(newFile("/home/sumit/employee.json"), Employee.class);
} 
catch (JsonGenerationException e){
    e.printStackTrace();
}

Weitere Informationen finden Sie unter folgendem Link .


4

Die häufigsten Antworten auf dieser Seite verwenden zu einfache Beispiele wie Objekte mit einer Eigenschaft (z. B. {Name: Wert}). Ich denke, dass ein noch einfaches, aber reales Beispiel jemandem helfen kann.

Dies ist also der von der Google Translate API zurückgegebene JSON:

{
  "data": 
     {
        "translations": 
          [
            {
              "translatedText": "Arbeit"
             }
          ]
     }
}

Ich möchte den Wert des Attributs "translateText", z. B. "Arbeit", mit Gson von Google abrufen.

Zwei mögliche Ansätze:

  1. Rufen Sie nur ein benötigtes Attribut ab

    String json  = callToTranslateApi("work", "de");
    JsonObject jsonObject = new JsonParser().parse(json).getAsJsonObject();
    return jsonObject.get("data").getAsJsonObject()
            .get("translations").getAsJsonArray()
            .get(0).getAsJsonObject()
            .get("translatedText").getAsString();
  2. Erstellen Sie ein Java-Objekt aus JSON

    class ApiResponse {
        Data data;      
        class Data {
            Translation[] translations;         
            class Translation {
                String translatedText;
            }
         }
     }

    ...

     Gson g = new Gson();
     String json =callToTranslateApi("work", "de");
     ApiResponse response = g.fromJson(json, ApiResponse.class);
     return response.data.translations[0].translatedText;

4

Dazu müssen Sie zunächst eine Implementierungsbibliothek auswählen .

Die Java-API für die JSON-Verarbeitung (JSR 353) bietet tragbare APIs zum Parsen, Generieren, Transformieren und Abfragen von JSON mithilfe von Objektmodell- und Streaming-APIs.

Die Referenzimplementierung finden Sie hier: https://jsonp.java.net/

Hier finden Sie eine Liste der Implementierungen von JSR 353:

Welche API implementiert JSR-353 (JSON)?

Und um Ihnen bei der Entscheidung zu helfen ... Ich habe auch diesen Artikel gefunden:

http://blog.takipi.com/the-ultimate-json-library-json-simple-vs-gson-vs-jackson-vs-json/

Wenn Sie sich für Jackson entscheiden, finden Sie hier einen guten Artikel über die Konvertierung zwischen JSON nach / von Java mit Jackson: https://www.mkyong.com/java/how-to-convert-java-object-to-from-json- Jackson/

Ich hoffe es hilft!


Sie zeigen auf Version 1 der Jackson-Bibliothek. Es wird dringend empfohlen, die aktuelle Version der Jackson-Bibliothek zu verwenden.
Herbert Yu

4

Sie können Jayway JsonPath verwenden . Unten finden Sie einen GitHub-Link mit Quellcode, POM-Details und guter Dokumentation.

https://github.com/jayway/JsonPath

Bitte befolgen Sie die folgenden Schritte.

Schritt 1 : Fügen Sie die Jayway-JSON-Pfadabhängigkeit mit Maven in Ihren Klassenpfad ein oder laden Sie die JAR-Datei herunter und fügen Sie sie manuell hinzu.

<dependency>
            <groupId>com.jayway.jsonpath</groupId>
            <artifactId>json-path</artifactId>
            <version>2.2.0</version>
</dependency>

Schritt 2 : Bitte speichern Sie Ihren Eingabe-JSON als Datei für dieses Beispiel. In meinem Fall habe ich Ihren JSON als sampleJson.txt gespeichert. Beachten Sie, dass Sie ein Komma zwischen pageInfo und Posts verpasst haben.

Schritt 3 : Lesen Sie den JSON-Inhalt aus der obigen Datei mit bufferedReader und speichern Sie ihn als String.

BufferedReader br = new BufferedReader(new FileReader("D:\\sampleJson.txt"));

        StringBuilder sb = new StringBuilder();
        String line = br.readLine();

        while (line != null) {
            sb.append(line);
            sb.append(System.lineSeparator());
            line = br.readLine();
        }
        br.close();
        String jsonInput = sb.toString();

Schritt 4 : Analysieren Sie Ihre JSON-Zeichenfolge mit dem jayway JSON-Parser.

Object document = Configuration.defaultConfiguration().jsonProvider().parse(jsonInput);

Schritt 5 : Lesen Sie die Details wie unten.

String pageName = JsonPath.read(document, "$.pageInfo.pageName");
String pagePic = JsonPath.read(document, "$.pageInfo.pagePic");
String post_id = JsonPath.read(document, "$.posts[0].post_id");

System.out.println("$.pageInfo.pageName " + pageName);
System.out.println("$.pageInfo.pagePic " + pagePic);
System.out.println("$.posts[0].post_id " + post_id);

Die Ausgabe wird sein :

$.pageInfo.pageName = abc
$.pageInfo.pagePic = http://example.com/content.jpg
$.posts[0].post_id  = 123456789012_123456789012

3

Ich habe JSON wie folgt:

{
   "pageInfo": {
         "pageName": "abc",
         "pagePic": "http://example.com/content.jpg"
    }
}

Java-Klasse

class PageInfo {

    private String pageName;
    private String pagePic;

    // Getters and setters
}

Code zum Konvertieren dieses JSON in eine Java-Klasse.

    PageInfo pageInfo = JsonPath.parse(jsonString).read("$.pageInfo", PageInfo.class);

Maven

<dependency>
    <groupId>com.jayway.jsonpath</groupId>
    <artifactId>json-path</artifactId>
    <version>2.2.0</version>
</dependency>

2

Man kann verwenden Apache @Model Anmerkung erstellen Java Modellklassen repräsentieren Struktur von JSON - Dateien und verwenden sie verschiedene Elemente in der für den Zugriff auf JSON Baum. Im Gegensatz zu anderen Lösungen funktioniert diese vollständig ohne Reflexion und ist daher für Umgebungen geeignet, in denen Reflexion unmöglich ist oder einen erheblichen Overhead mit sich bringt.

Es gibt ein Beispiel für ein Maven-Projekt, das die Verwendung zeigt. Zunächst definiert es die Struktur:

@Model(className="RepositoryInfo", properties = {
    @Property(name = "id", type = int.class),
    @Property(name = "name", type = String.class),
    @Property(name = "owner", type = Owner.class),
    @Property(name = "private", type = boolean.class),
})
final class RepositoryCntrl {
    @Model(className = "Owner", properties = {
        @Property(name = "login", type = String.class)
    })
    static final class OwnerCntrl {
    }
}

Anschließend werden die generierten Klassen RepositoryInfo und Owner verwendet, um den bereitgestellten Eingabestream zu analysieren und dabei bestimmte Informationen abzurufen:

List<RepositoryInfo> repositories = new ArrayList<>();
try (InputStream is = initializeStream(args)) {
    Models.parse(CONTEXT, RepositoryInfo.class, is, repositories);
}

System.err.println("there is " + repositories.size() + " repositories");
repositories.stream().filter((repo) -> repo != null).forEach((repo) -> {
    System.err.println("repository " + repo.getName() + 
        " is owned by " + repo.getOwner().getLogin()
    );
})

Das ist es! Darüber hinaus gibt es hier eine Live-Übersicht, die ein ähnliches Beispiel zusammen mit der asynchronen Netzwerkkommunikation zeigt.


2

jsoniter(jsoniterator) ist eine relativ neue und einfache json-Bibliothek, die einfach und schnell gestaltet wurde. Alles, was Sie tun müssen, um JSON-Daten zu deserialisieren, ist

JsonIterator.deserialize(jsonData, int[].class);

Wo jsonDataist eine Zeichenfolge von JSON-Daten.

Weitere Informationen finden Sie auf der offiziellen Website .


1

Wir können die JSONObject-Klasse verwenden, um eine JSON-Zeichenfolge in ein JSON-Objekt zu konvertieren und über das JSON-Objekt zu iterieren. Verwenden Sie den folgenden Code.

JSONObject jObj = new JSONObject(contents.trim());
Iterator<?> keys = jObj.keys();

while( keys.hasNext() ) {
  String key = (String)keys.next();
  if ( jObj.get(key) instanceof JSONObject ) {           
    System.out.println(jObj.getString(String key));
  }
}

2
Dies ist nur Android
omubomír


1
@DermotCanniffe es ist nur Android.
user4020527

1

Sie können die DSM- Stream-Parsing-Bibliothek zum Parsen komplexer JSON- und XML-Dokumente verwenden. DSM analysiert Daten nur einmal und lädt nicht alle Daten in den Speicher.

Angenommen, wir haben eine Page- Klasse, um bestimmte JSON-Daten zu deserialisieren.

Seitenklasse

public class Page {
    private String pageName;
    private String pageImage;
    private List<Sting> postIds;

    // getter/setter

}

Erstellen Sie eine Yaml-Zuordnungsdatei.

result:
  type: object     # result is array
  path: /posts
  fields:
    pageName:
        path: /pageInfo/pageName
    pageImage:
        path: /pageInfo/pagePic
    postIds:
      path: post_id
      type: array

Verwenden Sie DSM, um Felder zu extrahieren.

DSM dsm=new DSMBuilder(new File("path-to-yaml-config.yaml")).create(Page.class);
Page page= (Page)dsm.toObject(new path-to-json-data.json");

Seite Variable Json serialisiert:

{
  "pageName" : "abc",
  "pageImage" : "http://example.com/content.jpg",
  "postIds" : [ "123456789012_123456789012" ]
}

DSM ist sehr gut für komplexe JSON und XML.


0

Sie können JsonNodeeine strukturierte Baumdarstellung Ihrer JSON-Zeichenfolge verwenden. Es ist Teil der allgegenwärtigen Jackson- Bibliothek, die allgegenwärtig ist.

ObjectMapper mapper = new ObjectMapper();
JsonNode yourObj = mapper.readTree("{\"k\":\"v\"}");
Durch die Nutzung unserer Website bestätigen Sie, dass Sie unsere Cookie-Richtlinie und Datenschutzrichtlinie gelesen und verstanden haben.
Licensed under cc by-sa 3.0 with attribution required.