Testowanie dwóch obiektów JSON pod kątem równości, ignorując kolejność dzieci w Javie


233

Szukam biblioteki analizującej JSON, która obsługuje porównywanie dwóch obiektów JSON ignorujących kolejność elementów podrzędnych, szczególnie do testowania jednostkowego JSON powracającego z usługi WWW.

Czy którakolwiek z głównych bibliotek JSON obsługuje to? Biblioteka org.json po prostu porównuje odniesienia.


1
Nie można serializować obu obiektów do reprezentacji ciągów i porównywać? Chyba wszystkie biblioteki obsługują toString()konwersję obiektu na JSONciąg.
— Teja Kantamneni,

47
Zakłada to, że kolejność serializacji do i z ciągów znaków jest zawsze taka sama. Nie czuję się dobrze, przyjmując takie założenie.
— Jeff

Masz rację Jeff, to wcale nie jest bezpieczne. Ten test pokazuje scenariusz, w którym odwzorowania są takie same, ale toString () nie zwraca tego samego wyniku: gist.github.com/anonymous/5974797 . Wynika to z faktu, że podstawowa HashMap może się powiększać, a jeśli usuniesz klucze, wewnętrzna tablica HashMap się nie kurczy.
— Guillaume Perrot

Odpowiedzi:


84

Jako ogólny punkt architektoniczny zwykle odradzam uwalnianie zależności od określonego formatu serializacji poza warstwę pamięci / sieci; dlatego najpierw zaleciłbym rozważenie przetestowania równości między własnymi obiektami aplikacji, a nie ich manifestacjami JSON.

Powiedziawszy to, jestem obecnie wielkim fanem Jacksona, który mój szybki odczyt ich implementacji ObjectNode.equals () sugeruje, czy zestaw porównawczy członkostwa, który chcesz:

public boolean equals(Object o)
{
    if (o == this) return true;
    if (o == null) return false;
    if (o.getClass() != getClass()) {
        return false;
    }
    ObjectNode other = (ObjectNode) o;
    if (other.size() != size()) {
        return false;
    }
    if (_children != null) {
        for (Map.Entry<String, JsonNode> en : _children.entrySet()) {
            String key = en.getKey();
            JsonNode value = en.getValue();

            JsonNode otherValue = other.get(key);

            if (otherValue == null || !otherValue.equals(value)) {
                return false;
            }
        }
    }
    return true;
}

Ta metoda nie jest symetryczna, ponieważ testuje jedynie relacje „podzbioru” dzieci, a nie równość. „inny” obiekt może mieć więcej dzieci niż u dzieci, a ta metoda nadal zwróciłaby wartość true.
— Yoni

23
@Yoni: Nieprawda, ponieważ istnieje porównanie rozmiarów. Muszą mieć dokładnie taką samą liczbę dzieci, jak i te same dzieci. @Jolly Roger: W tym przypadku nie serializuję obiektu z JSON z powrotem do POJO, ale wysyłając JSON system, który to robi, nie mogę polegać na tym, że odsyła go w dokładnie takim samym formacie, w jakim wysłałem to.
— Jeff

1
@Jeff Czy to działało dla Ciebie? W junit assertEquals kończy się niepowodzeniem. Projekt używa starej wersji (1.5), fyi.
— ronnyfm,

1
Myślę, że brakuje ci testów wysokiego poziomu, jeśli nie zapewniasz JSON. Możesz mieć cienki test, który wysyła żądanie HTTP i odpowiada oczekiwanym JSON - jest to główne zachowanie funkcjonalne usługi internetowej.
— mogronalol

Tylko niewielka uwaga dotycząca wydajności: kod, który porównuje „wartość” z „otherValue”, można uprościć, jeśli (wartość.equals (other.get (klucz)) zwróci wartość false; jako że „wartość” z pewnością nie jest równa zeru i Metoda equals () JsonNode'a powinna zaakceptować argument zerowy
— Tillmann

154

Wypróbuj JSONAssert w Skyscreamer .

Jego zakaz ścisłe tryb ma dwie główne zalety, które czynią go mniej kruche:

  • Rozszerzalność obiektu (np. Przy oczekiwanej wartości {id: 1} , to i tak dałoby wynik: {id: 1, moredata: 'x'} .)
  • Luźna kolejność tablic (np. [„Pies”, „kot”] == [„kot”, „pies”])

W trybie ścisłym zachowuje się bardziej jak klasa testowa json-lib.

Test wygląda mniej więcej tak:

@Test
public void testGetFriends() {
    JSONObject data = getRESTData("/friends/367.json");
    String expected = "{friends:[{id:123,name:\"Corby Page\"}"
        + ",{id:456,name:\"Solomon Duskis\"}]}";
    JSONAssert.assertEquals(expected, data, false);
}

Parametry w wywołaniu JSONAssert.assertEquals () są oczekiwane : JSONString , actualDataString i isStrict .

Komunikaty wyników są dość wyraźne, co jest ważne przy porównywaniu naprawdę dużych obiektów JSON.


18
Korzystałem z tego rozwiązania, ale właśnie odkryłem, że możesz również podać wybrany przez Ciebie JSONCompareMode. Jednym z nich jest NON_EXTENSIBLE. Więc masz coś takiego: JSONAssert.assertEquals(expected, data, JSONCompareMode.NON_EXTENSIBLE);Tryb NON_EXTENSIBLE oznacza, że ​​wszelkie nowe lub brakujące pola powodują awarie, ale kolejność nie. Użycie false spowoduje uruchomienie trybu łagodnego, który nie zgłosi żadnych dodatkowych lub brakujących elementów potomnych.
— Dan Temple,

1
Tryb porównania NON_EXTENSIBLE jest dokładnie tym , czego szukałem. Dzięki za to, Dan.
— ThoughtCrhyme,

Zanim się podekscytuję: czy ta obsługa zagnieżdża również obiekty JSON i tablice? :)
— Christian

2
Ludzie mogą chcieć wziąć pod uwagę ten problem JSONassert przed użyciem biblioteki: oznacza to, że istnieją obecnie potencjalne problemy z licencjonowaniem w zależności od biblioteki.
— Chriki,

3
Naprawiono błąd JSONAssert nr 44, zastępując bibliotekę clean-room w PR 67, wydany dzisiaj jako JSONAssert 1.4.0.
— Carter Page

49

Korzystanie z GSON

JsonParser parser = new JsonParser();
JsonElement o1 = parser.parse("{a : {a : 2}, b : 2}");
JsonElement o2 = parser.parse("{b : 2, a : {a : 2}}");
assertEquals(o1, o2);

Edycja: Od wersji GSON v2.8.6 metoda instancji JsonParser.parsejest przestarzała. Musisz użyć metody statycznej JsonParser.parseString:

JsonElement o1 = JsonParser.parseString("{a : {a : 2}, b : 2}");
JsonElement o2 = JsonParser.parseString("{b : 2, a : {a : 2}}");
assertEquals(o1, o2);

Działa dla mnie w GSON 2.8.2.
— Tom Saleeba

1
nie działa, jeśli elementy jsonArray nie są w porządku. wersja 2.8.2
— Naveen Kumar RB

1
Nie działa dla mnie, jeśli kolejność obiektu / elementu jest inna
— Jknair

Działa to dla mnie, ponieważ chciałem go tylko do testu jednostkowego, w którym właściwości dwóch jsonów miały tę samą kolejność
— GabrielBB

@GabrielBB Powinieneś edytować pytanie i wskazać, w jakiej wersji API jest przestarzałe, iw jakiej wersji zaczyna działać nowy styl kodu.
— jasne

30

Zrobiłbym następujące,

JSONObject obj1 = /*json*/;
JSONObject obj2 = /*json*/;

ObjectMapper mapper = new ObjectMapper();

JsonNode tree1 = mapper.readTree(obj1.toString());
JsonNode tree2 = mapper.readTree(obj2.toString());

return tree1.equals(tree2);

Jeśli używasz już Jacksona, to najlepsza odpowiedź IMHO.
— Christoph Dietze

18
ale myślę, że jest to ścisłe porównanie. Zwróci wartość false dla dwóch równych jsonów o różnej kolejności elementów.
— Deadpool

@deadpool zasada jest zdrowa, wystarczy zmienić porównanie, aby być bardziej zaangażowanym (na przykład sprawdzanie kluczowych pól, a nie zwykłych drzewek).
— jwenting

To najlepsza odpowiedź na świecie. Nie tylko odpowiada teraz na moje pytanie, ale także odpowiada na prawie każde porównanie obiektów, które musimy wykonać. dzięki, joshu.
— Luiz Feijão Veronesi

2
@deadpool, być może było to ścisłe porównanie, ale teraz nie jest ścisłe.
— Andrei Damian-Fekete

18

Możesz spróbować użyć klasy JSONAssert json-lib :

JSONAssert.assertEquals(
  "{foo: 'bar', baz: 'qux'}",
  JSONObject.fromObject("{foo: 'bar', baz: 'xyzzy'}")
);

Daje:

junit.framework.ComparisonFailure: objects differed at key [baz]; expected:<[qux]> but was:<[xyzzy]>

Lub nawet prościej: JSONAssert.assertJsonEquals („{foo: 'bar', baz: 'qux'} ', {foo:' bar ', baz:' xyzzy '}”);
— Rob Juurlink

2
Chociaż to rozwiązanie działa w przypadku kolejności elementów danych w JSON, zakończy się niepowodzeniem, jeśli kolejność elementów w tablicach nie będzie zgodna. Jeśli kod używa zestawu, który jest na przykład konwertowany na JSON. Następujące porównanie JSON nie powiedzie się: JSONAssert.assertJsonEquals( "{foo: 'bar', list: [{test: '1'}, {rest: '2'}] }", "{ foo: 'bar', list: [{rest: '2'}, {test: '1'}] }"); Komunikat:junit.framework.AssertionFailedError: : : objects differed at key [list];: arrays first differed at element [0];: objects differed at key [test];
— Dan Temple

Tak, jest to ograniczenie Json :(. Json.org pokazuje, że nie ma nieuporządkowanego tokenu kolekcji. {} Może otaczać tylko pary klucz-wartość. Jest to bardzo irytujące
— Merk

15

Użyj tej biblioteki: https://github.com/lukas-krecan/JsonUnit

Pom:

<dependency>
    <groupId>net.javacrumbs.json-unit</groupId>
    <artifactId>json-unit</artifactId>
    <version>1.5.0</version>
    <scope>test</scope>
</dependency>

IGNORING_ARRAY_ORDER - ignoruje kolejność w tablicach

assertJsonEquals("{\"test\":[1,2,3]}",
  "{\"test\":  [3,2,1]}",
  when(IGNORING_ARRAY_ORDER)
);

czy możesz dodać więcej komentarzy na temat tego, jak możemy go używać? Dodaję go do mojej pom, ale potrzebujemy doc, aby zrozumieć, jak go używać
— Ran Adler,

pewna obsługa jest bardzo prosta: dodaj to do pom. <dependency> <groupId> net.javacrumbs.json-unit </groupId> <artifactId> json-unit </artifactId> <version> 1.5.0 </version> <scope> test </scope> </dependency>
— chethu

10x spojrzałem na instrukcję pod linkiem i znalazłem ją :)
— Ran Adler

12

Jeśli już używasz JUnit, najnowsza wersja zawiera teraz Hamcrest. Jest to ogólna struktura dopasowywania (szczególnie przydatna do testowania jednostkowego), którą można rozszerzyć w celu zbudowania nowych dopasowań.

Istnieje mała biblioteka open source o nazwie hamcrest-jsonz dopasowaniami JSON. Jest dobrze udokumentowany, przetestowany i obsługiwany. Poniżej znajdują się przydatne linki:

Przykładowy kod wykorzystujący obiekty z biblioteki JSON org.json.simple:

Assert.assertThat(
    jsonObject1.toJSONString(),
    SameJSONAs.sameJSONAs(jsonObject2.toJSONString()));

Opcjonalnie możesz (1) zezwolić na tablice „dowolnego rzędu” i (2) zignorować dodatkowe pola.

Ponieważ istnieje wiele bibliotek JSON for Java ( Jackson, GSON, json-lib, itd), jest przydatna, że hamcrest-jsontekst podpory JSON (jak java.lang.String), a także obiekty wspierające natywnie z JSON biblioteki Douglasa Crockforda użytkownika org.json.

Wreszcie, jeśli nie używasz JUnit, możesz użyć Hamcrest bezpośrednio do asercji. ( Pisałem o tym tutaj. )


Jaka jest zaleta używania dopasowywania hamcrast zamiast bezpośredniego używania JSONAssert?
— Johannes,

2
@Johannes: Tylko styl.
— kevinarpe

Źródła hamcrest-json mają obecnie datę ostatniego zatwierdzenia w 2012 r. Może nie być już tak dobrze wspierane.
— Thorbjørn Ravn Andersen

11

Możesz wypróbować JsonUnit . Może porównywać dwa obiekty JSON i zgłaszać różnice. Jest zbudowany na Jacksonie.

Na przykład

assertJsonEquals("{\"test\":1}", "{\n\"test\": 2\n}");

Prowadzi do

java.lang.AssertionError: JSON documents are different:
Different value found in node "test". Expected 1, got 2.

6

Jedną rzeczą, którą zrobiłem i działa cuda, jest odczytanie obu obiektów do HashMap, a następnie porównanie ze zwykłą funkcją assertEquals (). Wywoła metodę haszaps równą (), która rekurencyjnie porównuje wszystkie obiekty w środku (będą to albo inne haszapy, albo jakiś obiekt o pojedynczej wartości, taki jak łańcuch lub liczba całkowita). Dokonano tego przy użyciu analizatora składni JSON firmy Codehaus.

assertEquals(mapper.readValue(expectedJson, new TypeReference<HashMap<String, Object>>(){}), mapper.readValue(actualJson, new TypeReference<HashMap<String, Object>>(){}));

Podobne podejście można zastosować, jeśli obiekt JSON jest tablicą.


6

Używam tego i działa dobrze dla mnie (z org.json. *):

package com.project1.helpers;

import org.json.JSONArray;
import org.json.JSONException;
import org.json.JSONObject;

import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;

public class JSONUtils {

    public static boolean areEqual(Object ob1, Object ob2) throws JSONException {
        Object obj1Converted = convertJsonElement(ob1);
        Object obj2Converted = convertJsonElement(ob2);
        return obj1Converted.equals(obj2Converted);
    }

    private static Object convertJsonElement(Object elem) throws JSONException {
        if (elem instanceof JSONObject) {
            JSONObject obj = (JSONObject) elem;
            Iterator<String> keys = obj.keys();
            Map<String, Object> jsonMap = new HashMap<>();
            while (keys.hasNext()) {
                String key = keys.next();
                jsonMap.put(key, convertJsonElement(obj.get(key)));
            }
            return jsonMap;
        } else if (elem instanceof JSONArray) {
            JSONArray arr = (JSONArray) elem;
            Set<Object> jsonSet = new HashSet<>();
            for (int i = 0; i < arr.length(); i++) {
                jsonSet.add(convertJsonElement(arr.get(i)));
            }
            return jsonSet;
        } else {
            return elem;
        }
    }
}

4

W przypadku org.json wdrożyłem własne rozwiązanie, metodę porównywalną z instancjami JSONObject. W tym projekcie nie pracowałem ze złożonymi obiektami JSON, więc nie wiem, czy to działa we wszystkich scenariuszach. Biorąc pod uwagę, że używam tego w testach jednostkowych, nie wkładałem wysiłku w optymalizacje. Oto on:

public static boolean jsonObjsAreEqual (JSONObject js1, JSONObject js2) throws JSONException {
    if (js1 == null || js2 == null) {
        return (js1 == js2);
    }

    List<String> l1 =  Arrays.asList(JSONObject.getNames(js1));
    Collections.sort(l1);
    List<String> l2 =  Arrays.asList(JSONObject.getNames(js2));
    Collections.sort(l2);
    if (!l1.equals(l2)) {
        return false;
    }
    for (String key : l1) {
        Object val1 = js1.get(key);
        Object val2 = js2.get(key);
        if (val1 instanceof JSONObject) {
            if (!(val2 instanceof JSONObject)) {
                return false;
            }
            if (!jsonObjsAreEqual((JSONObject)val1, (JSONObject)val2)) {
                return false;
            }
        }

        if (val1 == null) {
            if (val2 != null) {
                return false;
            }
        }  else if (!val1.equals(val2)) {
            return false;
        }
    }
    return true;
}

1
Ponieważ wspomniałeś o optymalizacji :), jeśli val1jest null, otrzymasz wyjątek NullPointerException z tego koduif (!val1.equals(val2)) {
— JohnDoDo

Zdarza się także najlepszemu z nas :). +1 za naprawienie go w swojej odpowiedzi.
— JohnDoDo

punkt wzięty :) Mam nadzieję, że nie zdobędzie on jednak zbyt wielu głosów, w przeciwnym razie będzie dużo wsparcia.
— Victor Ionescu

1
Nie zastanawiałeś się, czy js2jest, nullczy nie, kiedy js1nie manull
— Xiao

Ten kod nie działa dla zagnieżdżonych obiektów / sekwencji.
— FabienB


2

Wziąłbym bibliotekę pod adresem http://json.org/java/ i zmodyfikowałem equalsmetodę JSONObject i JSONArray, aby przeprowadzić głęboki test równości. Aby upewnić się, że działa bez względu na kolejność dzieci, wystarczy wymienić wewnętrzną mapę na TreeMaplub użyć czegoś podobnego Collections.sort().


4
nie jest tak świetny - naprawdę powinien był mieć kod do porównania JSON.
— Chii

Ale wyobraź sobie pisanie tego kodu, w którym JSON może być dowolnym elementem w dowolnej strukturze ... napisz porównanie! To jak pisanie porównania dla wszystkich typów stron HTML.
— JPM,

2

Spróbuj tego:

public static boolean jsonsEqual(Object obj1, Object obj2) throws JSONException

    {
        if (!obj1.getClass().equals(obj2.getClass()))
        {
            return false;
        }

        if (obj1 instanceof JSONObject)
        {
            JSONObject jsonObj1 = (JSONObject) obj1;

            JSONObject jsonObj2 = (JSONObject) obj2;

            String[] names = JSONObject.getNames(jsonObj1);
            String[] names2 = JSONObject.getNames(jsonObj1);
            if (names.length != names2.length)
            {
                return false;
            }

            for (String fieldName:names)
            {
                Object obj1FieldValue = jsonObj1.get(fieldName);

                Object obj2FieldValue = jsonObj2.get(fieldName);

                if (!jsonsEqual(obj1FieldValue, obj2FieldValue))
                {
                    return false;
                }
            }
        }
        else if (obj1 instanceof JSONArray)
        {
            JSONArray obj1Array = (JSONArray) obj1;
            JSONArray obj2Array = (JSONArray) obj2;

            if (obj1Array.length() != obj2Array.length())
            {
                return false;
            }

            for (int i = 0; i < obj1Array.length(); i++)
            {
                boolean matchFound = false;

                for (int j = 0; j < obj2Array.length(); j++)
                {
                    if (jsonsEqual(obj1Array.get(i), obj2Array.get(j)))
                    {
                        matchFound = true;
                        break;
                    }
                }

                if (!matchFound)
                {
                    return false;
                }
            }
        }
        else
        {
            if (!obj1.equals(obj2))
            {
                return false;
            }
        }

        return true;
    }

w jsonArrays zwraca wartość true, jeśli niektóre elementy się pokrywają, w przeciwieństwie do wszystkich elementów.
— matiasg

@matiasg - czy if (obj1Array.length() != obj2Array.length())nie gwarantuje, że wszystkie elementy się pokrywają?
— kwah

3
@kwah: nope. Rozważ ten przykład: obj1Array = [1,1,1], obj2Array = [1,2,3]. To zwróci prawdę. Ponadto, nawet jeśli elementy się pokrywają, powinny być w tej samej kolejności. Zwróciłoby to również prawdę dla [1,2,3] i [2,3,1], co jest błędne
— matiasg


2

Karate jest dokładnie tym, czego szukasz. Oto przykład:

* def myJson = { foo: 'world', hey: 'ho', zee: [5], cat: { name: 'Billie' } }
* match myJson = { cat: { name: 'Billie' }, hey: 'ho', foo: 'world', zee: [5] }

(wyłączenie odpowiedzialności: tutaj programista)


2

Do porównania jsonów polecam użycie JSONCompare: https://github.com/fslev/json-compare

// Compare by regex
String expected = "{\"a\":\".*me.*\"}";
String actual = "{\"a\":\"some text\"}";
JSONCompare.assertEquals(expected, actual);  // True

// Check expected array has no extra elements
String expected = "[1,\"test\",4,\"!.*\"]";
String actual = "[4,1,\"test\"]";
JSONCompare.assertEquals(expected, actual);  // True

// Check expected array has no numbers
String expected = "[\"\\\\\\d+\"]";
String actual = "[\"text\",\"test\"]";
JSONCompare.assertEquals(expected, actual);  // True

// Check expected array has no numbers
String expected = "[\"\\\\\\d+\"]";
String actual = "[2018]";
JSONCompare.assertNotEquals(expected, actual);  // True

0

Dla takich jak ja, którzy chcą to zrobić z Jacksonem, możesz użyć json-unit .

JsonAssert.assertJsonEquals(jsonNode1, jsonNode2);

Błędy dają użyteczne informacje zwrotne na temat rodzaju niedopasowania:

java.lang.AssertionError: JSON documents have different values:
Different value found in node "heading.content[0].tag[0]". Expected 10209, got 10206.

0

Nic innego nie działało całkiem dobrze, więc napisałem to:

private boolean jsonEquals(JsonNode actualJson, JsonNode expectJson) {
    if(actualJson.getNodeType() != expectJson.getNodeType()) return false;

    switch(expectJson.getNodeType()) {
    case NUMBER:
        return actualJson.asDouble() == expectJson.asDouble();
    case STRING:
    case BOOLEAN:
        return actualJson.asText().equals(expectJson.asText());
    case OBJECT:
        if(actualJson.size() != expectJson.size()) return false;

        Iterator<String> fieldIterator = actualJson.fieldNames();
        while(fieldIterator.hasNext()) {
            String fieldName = fieldIterator.next();
            if(!jsonEquals(actualJson.get(fieldName), expectJson.get(fieldName))) {
                return false;
            }
        }
        break;
    case ARRAY:
        if(actualJson.size() != expectJson.size()) return false;
        List<JsonNode> remaining = new ArrayList<>();
        expectJson.forEach(remaining::add);
        // O(N^2)   
        for(int i=0; i < actualJson.size(); ++i) {
            boolean oneEquals = false;
            for(int j=0; j < remaining.size(); ++j) {
                if(jsonEquals(actualJson.get(i), remaining.get(j))) {
                    oneEquals = true;
                    remaining.remove(j);
                    break;
                }
            }
            if(!oneEquals) return false;
        }
        break;
    default:
        throw new IllegalStateException();
    }
    return true;
}

0

Poniższy kod będzie bardziej pomocny w porównaniu dwóch JsonObject, JsonArray, JsonPrimitive i JasonElements.

private boolean compareJson(JsonElement json1, JsonElement json2) {
        boolean isEqual = true;
        // Check whether both jsonElement are not null
        if (json1 != null && json2 != null) {

            // Check whether both jsonElement are objects
            if (json1.isJsonObject() && json2.isJsonObject()) {
                Set<Entry<String, JsonElement>> ens1 = ((JsonObject) json1).entrySet();
                Set<Entry<String, JsonElement>> ens2 = ((JsonObject) json2).entrySet();
                JsonObject json2obj = (JsonObject) json2;
                if (ens1 != null && ens2 != null) {
                    // (ens2.size() == ens1.size())
                    // Iterate JSON Elements with Key values
                    for (Entry<String, JsonElement> en : ens1) {
                        isEqual = isEqual && compareJson(en.getValue(), json2obj.get(en.getKey()));
                    }
                } else {
                    return false;
                }
            }

            // Check whether both jsonElement are arrays
            else if (json1.isJsonArray() && json2.isJsonArray()) {
                JsonArray jarr1 = json1.getAsJsonArray();
                JsonArray jarr2 = json2.getAsJsonArray();
                if (jarr1.size() != jarr2.size()) {
                    return false;
                } else {
                    int i = 0;
                    // Iterate JSON Array to JSON Elements
                    for (JsonElement je : jarr1) {
                        isEqual = isEqual && compareJson(je, jarr2.get(i));
                        i++;
                    }
                }
            }

            // Check whether both jsonElement are null
            else if (json1.isJsonNull() && json2.isJsonNull()) {
                return true;
            }

            // Check whether both jsonElement are primitives
            else if (json1.isJsonPrimitive() && json2.isJsonPrimitive()) {
                if (json1.equals(json2)) {
                    return true;
                } else {
                    return false;
                }
            } else {
                return false;
            }
        } else if (json1 == null && json2 == null) {
            return true;
        } else {
            return false;
        }
        return isEqual;
    }


0

Patrząc na odpowiedzi, spróbowałem JSONAssert, ale nie udało się. Więc użyłem Jacksona z zjsonpatch. Podałem szczegóły w odpowiedzi SO tutaj .


-5

To rozwiązanie jest dla mnie bardzo dobre:

try {           
                // Getting The Array "Courses" from json1 & json2   
                Courses1 =json1.getJSONArray(TAG_COURSES1);
                Courses2 = json2.getJSONArray(TAG_COURSES);

                //LOOP FOR JSON1
                for(int i = 0; i < Courses1.length(); i++){
                    //LOOP FOR JSON2
                    for(int ii = 0; ii < Courses2.length(); ii++){
                        JSONObject courses1 = Courses1.getJSONObject(i);
                        JSONObject courses2 = Courses2.getJSONObject(ii);

                        // Storing each json1 item in variable
                        int courseID1 = courses1.getInt(TAG_COURSEID1);
                        Log.e("COURSEID2:", Integer.toString(courseID1));
                        String Rating1 = courses1.getString(TAG_RATING1);
                        int Status1 = courses1.getInt(TAG_STATUS1);
                        Log.e("Status1:", Integer.toString(Status1));      //Put the actual value for Status1 in log.             

                        // Storing each json2 item in variable
                        int courseID2 = courses2.getInt(TAG_COURSEID);
                        Log.e("COURSEID2:", Integer.toString(courseID));   //Put the actual value for CourseID in log
                        String Title2 = courses2.getString(TAG_TITLE);                      
                        String instructor2 = courses2.getString(TAG_INSTRUCTOR);
                        String length2 = courses2.getString(TAG_LENGTH);
                        String rating2 = courses2.getString(TAG_RATING);
                        String subject2 = courses2.getString(TAG_SUBJECT);
                        String description2 = courses2.getString(TAG_DESCRIPTION);

                        //Status1 = 5 from json1; Incomplete, Status1 =-1 Complete 
                        if(Status1 == 5 && courseID2 == courseID1){                                  

                        // creating new HashMap
                        HashMap<String, String> map = new HashMap<String, String>();         
                        //Storing the elements if condition is true.
                        map.put(TAG_COURSEID, Integer.toString(courseID2)); //pend for compare
                        map.put(TAG_TITLE, Title2);
                        map.put(TAG_INSTRUCTOR, instructor2);
                        map.put(TAG_LENGTH, length2);
                        map.put(TAG_RATING, rating2);
                        map.put(TAG_SUBJECT, subject2); //show it
                        map.put(TAG_DESCRIPTION, description2);

                        //adding HashList to ArrayList
                        contactList.add(map);
                        }//if
                    }//for2 (json2)
                } //for1 (json1)                
            }//Try

Mam nadzieję, że pomoże to innym.


oczywiście, po prostu podaj swoje wartości i warunki oraz rodzaj widoku, w tym przypadku; Hashmapa nad widokiem listy.
— JLouis,

1
To
— dobry
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.