JSON Array iteración en Android / Java


148

Estoy creando una aplicación para Android que necesita descargarse y sincronizarse con una base de datos en línea, estoy enviando mi consulta desde la aplicación a una página php que devuelve las filas relevantes de una base de datos en formato JSON.

¿Puede alguien decirme la mejor manera de iterar a través de una matriz JSON?

Recibo una variedad de objetos:

[{json object},{json object},{json object}]

¿Cuál es el código más simple que podría usar para acceder a los JSONObjects en la matriz?

EDITAR: ahora que lo pienso, el método que usé para iterar el ciclo fue:

for (String row: json){
     id = row.getInt("id");
     name = row.getString("name");
     password = row.getString("password");
}

Así que supongo que de alguna manera pude convertir el Json devuelto en una matriz iterable. ¿Alguna idea de cómo podría lograr esto?

Pido disculpas por mi falta de valor, pero tuve esto funcionando a partir de un ejemplo que encontré en la web y desde entonces no he podido encontrarlo.


Respuestas:


67

Lo he hecho de dos maneras diferentes,

1.) hacer un mapa

        HashMap<String, String> applicationSettings = new HashMap<String,String>();
        for(int i=0; i<settings.length(); i++){
            String value = settings.getJSONObject(i).getString("value");
            String name = settings.getJSONObject(i).getString("name");
            applicationSettings.put(name, value);
        }

2.) haz un JSONArray de nombres

    JSONArray names = json.names();
    JSONArray values = json.toJSONArray(names);
    for(int i=0; i<values.length(); i++){
        if (names.getString(i).equals("description")){
            setDescription(values.getString(i));
        }
        else if (names.getString(i).equals("expiryDate")){
            String dateString = values.getString(i);
            setExpiryDate(stringToDateHelper(dateString)); 
        }
        else if (names.getString(i).equals("id")){
            setId(values.getLong(i));
        }
        else if (names.getString(i).equals("offerCode")){
            setOfferCode(values.getString(i));
        }
        else if (names.getString(i).equals("startDate")){
            String dateString = values.getString(i);
            setStartDate(stringToDateHelper(dateString));
        }
        else if (names.getString(i).equals("title")){
            setTitle(values.getString(i));
        }
    }

335

Creo que este código es corto y claro:

int id;
String name;
JSONArray array = new JSONArray(string_of_json_array);
for (int i = 0; i < array.length(); i++) {
    JSONObject row = array.getJSONObject(i);
    id = row.getInt("id");
    name = row.getString("name");
}

¿Es eso lo que estabas buscando?


3
Agradable y simple! ¡Funciona genial!
Kervin Ramen

55
tenga en cuenta que si envía una "matriz" que no tiene números consecutivos, debe usar JSONObject
max4ever

sí, es perfecto, pero si bien una gran cantidad de datos es muy lento en el procesamiento :(
Ahmad Arslan

@ArslanAhmad Si tiene una gran cantidad de datos, no desea construir toda la matriz de objetos json en la memoria. En su lugar, utilice un enfoque similar al SAX. Ver aquí: stackoverflow.com/questions/10657725/…
vipw

Esto no funciona para mí. obtengo una excepción JSON debido al corchete "{" que rodea el objeto?
filthy_wizard

7

Desafortunadamente, JSONArray no admite foreachdeclaraciones como:

for(JSONObject someObj : someJsonArray) {
    // do something about someObj
    ....
    ....
}


lo hace, pero devuelve un objeto no JSONObject
Error

3
La clase JSONArray no implementa la interfaz Iterable
Jorgesys

4

Cuando probé la sugerencia de @ vipw, me encontré con esta excepción: The method getJSONObject(int) is undefined for the type JSONArray

Esto funcionó para mí en su lugar:

int myJsonArraySize = myJsonArray.size();

for (int i = 0; i < myJsonArraySize; i++) {
    JSONObject myJsonObject = (JSONObject) myJsonArray.get(i);

    // Do whatever you have to do to myJsonObject...
}

Para Android, cambié myJsonArray.size () a myJsonArray.length () en su lugar
Rishiraj Purohit

3

Si está utilizando la implementación JSON.org Java , que es de código abierto, puede hacer que JSONArray implemente la Iterableinterfaz y agregar el siguiente método a la clase:

@Override
public Iterator iterator() {
    return this.myArrayList.iterator();
}

Esto hará que todas las instancias de JSONArray sean iterables, lo que significa que la for (Object foo : bar)sintaxis ahora funcionará con él (tenga en cuenta que foo tiene que ser un Objeto, porque JSONArrays no tiene un tipo declarado). Todo esto funciona porque la clase JSONArray está respaldada por una simple ArrayList, que ya es iterable. Me imagino que otras implementaciones de código abierto serían igual de fáciles de cambiar.


1
Lo interesante es que en un momento la implementación de JSON.org tenía un iterador en la clase JSONArray, pero lo eliminaron: github.com/douglascrockford/JSON-java/commit/…
vipw

@vipw Les había enviado un correo electrónico una vez sobre la implementación de Iterable, pero dijeron que, en última instancia, no podían porque rompería la compatibilidad con Java 1.4. Quizás por eso se eliminó en el commit.
Thunderforge

3

En matrices, busque:

JSONArray menuitemArray = popupObject.getJSONArray("menuitem"); 

2

Estás utilizando el mismo objeto Cast para cada entrada. En cada iteración, simplemente cambió el mismo objeto en lugar de crear uno nuevo.

Este código debería arreglarlo:

JSONArray jCastArr = jObj.getJSONArray("abridged_cast");
ArrayList<Cast> castList= new ArrayList<Cast>();

for (int i=0; i < jCastArr.length(); i++) {
    Cast person = new Cast();  // create a new object here
    JSONObject jpersonObj = jCastArr.getJSONObject(i);

    person.castId = (String) jpersonObj.getString("id");
    person.castFullName = (String) jpersonObj.getString("name");

    castList.add(person);
}
details.castList = castList;

1

Mientras itera sobre una matriz JSON (org.json.JSONArray, integrada en Android), tenga cuidado con los objetos nulos ; por ejemplo, puede obtener en "null"lugar de una cadena nula .

Un cheque puede verse así:

s[i] = array.isNull(i) ? null : array.getString(i);
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.