2010-11-12 44 views
27

Necesito analizar el objeto JSON a través de Qt. ¿Cuál es la forma más fácil/rápida de hacerlo?manera más fácil de analizar JSON en Qt 4.7

+0

Ver [Mejor JSON analizador para Qt? ] (http://stackoverflow.com/questions/1825892?tab=newest#tab-top). –

+0

Lo intenté, no funcionó – wael34218

+3

Parece que Qt5 tiene algunas clases de JSON. http://qt-project.org/doc/qt-5.0/qtcore/json.html –

Respuesta

15

Pruebe QJson.

QJson está desarrollado activamente (y utilizado por KDE, si no me equivoco). Lo mejor es verificar el código fuente directamente y compilarlo usted mismo. No hay dependencias con QJson (excepto Qt y CMake). Es muy sencillo de usar también, echar un vistazo a algunos ejemplos de uso:

http://qjson.sourceforge.net/usage/

7

Aquí es Qt style json codificador/decodificador

#include "json.h" 

#include <QScriptEngine> 
#include <QScriptValueIterator> 

Json::Json() 
{ 
} 


QString Json::encode(const QMap<QString,QVariant> &map) 
{ 
    QScriptEngine engine; 
    engine.evaluate("function toString() { return JSON.stringify(this) }"); 

    QScriptValue toString = engine.globalObject().property("toString"); 
    QScriptValue obj = encodeInner(map, &engine); 
    return toString.call(obj).toString(); 

} 

QMap<QString, QVariant> Json::decode(const QString &jsonStr) 
{ 
    QScriptValue object; 
    QScriptEngine engine; 
    object = engine.evaluate("(" + jsonStr + ")"); 
    return decodeInner(object); 
} 

QScriptValue Json::encodeInner(const QMap<QString,QVariant> &map, QScriptEngine* engine) 
{ 
    QScriptValue obj = engine->newObject(); 
    QMapIterator<QString, QVariant> i(map); 
    while (i.hasNext()) { 
     i.next(); 
     if (i.value().type() == QVariant::String) 
      obj.setProperty(i.key(), i.value().toString()); 
     else if (i.value().type() == QVariant::Int) 
      obj.setProperty(i.key(), i.value().toInt()); 
     else if (i.value().type() == QVariant::Double) 
      obj.setProperty(i.key(), i.value().toDouble()); 
     else if (i.value().type() == QVariant::List) 
      obj.setProperty(i.key(), qScriptValueFromSequence(engine, i.value().toList())); 
     else if (i.value().type() == QVariant::Map) 
      obj.setProperty(i.key(), encodeInner(i.value().toMap(), engine)); 
    } 
    return obj; 
} 


QMap<QString, QVariant> Json::decodeInner(QScriptValue object) 
{ 
    QMap<QString, QVariant> map; 
    QScriptValueIterator it(object); 
    while (it.hasNext()) { 
     it.next(); 
     if (it.value().isArray()) 
      map.insert(it.name(),QVariant(decodeInnerToList(it.value()))); 
     else if (it.value().isNumber()) 
      map.insert(it.name(),QVariant(it.value().toNumber())); 
     else if (it.value().isString()) 
      map.insert(it.name(),QVariant(it.value().toString())); 
     else if (it.value().isNull()) 
      map.insert(it.name(),QVariant()); 
     else if(it.value().isObject()) 
      map.insert(it.name(),QVariant(decodeInner(it.value()))); 
    } 
    return map; 
} 

QList<QVariant> Json::decodeInnerToList(QScriptValue arrayValue) 
{ 
    QList<QVariant> list; 
    QScriptValueIterator it(arrayValue); 
    while (it.hasNext()) { 
     it.next(); 
     if (it.name() == "length") 
      continue; 

     if (it.value().isArray()) 
      list.append(QVariant(decodeInnerToList(it.value()))); 
     else if (it.value().isNumber()) 
      list.append(QVariant(it.value().toNumber())); 
     else if (it.value().isString()) 
      list.append(QVariant(it.value().toString())); 
     else if (it.value().isNull()) 
      list.append(QVariant()); 
     else if(it.value().isObject()) 
      list.append(QVariant(decodeInner(it.value()))); 
    } 
    return list; 
} 
+0

Esto se ve muy bien ... pero no compila ... referencia indefinida a QScriptEngine :: newObject ...... y agregué #include en el archivo json.h. Incluso es posible usar esto con QT 4.8.1. ? – user568021

+0

@ user568021 Compila muy bien para mí con Qt 4.8.2. –

+0

¡Solución impresionante! Sería una buena biblioteca de solo encabezado, solo incluiría y usaría todo lo de la biblioteca de compilación con infinitas dependencias. Algo para convertir ese QMap en un objeto lo haría perfecto. Me las arreglé para hacer eso. Dejaré el código aquí para usarlo con tu código. – Jack

5

Sé que esta respuesta es tardía, pero recientemente he creado un proyecto para ayuda a crear código que se compila en Qt4 y Qt5 y trata con JSON.

https://code.google.com/p/qjson4/

Esta biblioteca se sangra a ser una gota en el reemplazo para QJsonDocument en Qt4 y utilizará las clases de Qt cuando se utiliza en QT5. Entonces debería ser una transición bastante suave. No está 100% completo, pero las principales características están ahí :-).

+0

Gran respuesta que he votado en sentido ascendente. Solo una pequeña adición a su código en 'QJsonValue.h':' Q_DECLARE_METATYPE (QJsonValue) 'para hacer que esta clase sea utilizable en algunos casos especiales. – jonathanzh

+0

Claro, puedo agregar que :-) –

18

JSON análisis es ahora compatible con Qt 5. Aquí se explica cómo cargar y analizar un documento:

#include <QByteArray> 
#include <QFile> 
#include <QJsonObject> 
#include <QJsonDocument> 

// ... 

// Read JSON file 
QFile file("/path/to/file.json"); 
file.open(QIODevice::ReadOnly); 
QByteArray rawData = file.readAll(); 

// Parse document 
QJsonDocument doc(QJsonDocument::fromJson(rawData)); 

// Get JSON object 
QJsonObject json = doc.object(); 

// Access properties 
qDebug() << json["something"].toString(); 
+5

La pregunta es sobre la versión 4.7 – dtech

+1

Gracias, esto me ayudó. – Goddard

0

recomendaría qjson-backport, ya que utiliza la misma API como en QT5.

Puede cargar la biblioteca condicionalmente cuando usa Qt4, y usar la implementación predeterminada cuando usa Qt5.

Mi archivo qjson.pri parece:

!greaterThan(QT_MAJOR_VERSION, 4): { 

    INCLUDEPATH += \ 
     $$PWD 

    SOURCES += \ 
     $$PWD/qjson.cpp \ 
     $$PWD/qjsonarray.cpp \ 
     $$PWD/qjsondocument.cpp \ 
     $$PWD/qjsonobject.cpp \ 
     $$PWD/qjsonparser.cpp \ 
     $$PWD/qjsonvalue.cpp \ 
     $$PWD/qjsonwriter.cpp 

    HEADERS += \ 
     $$PWD/qjson_p.h \ 
     $$PWD/qjsonarray.h \ 
     $$PWD/qjsondocument.h \ 
     $$PWD/qjsonobject.h \ 
     $$PWD/qjsonparser_p.h \ 
     $$PWD/qjsonvalue.h \ 
     $$PWD/qjsonwriter_p.h 

} 
Cuestiones relacionadas