QDomDocument Strukturparser

Alles rund um die Programmierung mit Qt
Antworten
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

QDomDocument Strukturparser

Beitrag von Necropsy »

Guten Tag,

Ich habe mit der QT Klasse QDomDocument versucht einen parser für XML zu schreiben allerdings komm ich nicht so ganz vorran. Ich komme einfach nicht über den Punkt hinaus die unterelemente von den Tags <message> zu wechseln.

ein Beispiel:

Code: Alles auswählen

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE TS>
<TS version="2.0" language="en_US" sourcelanguage="en_GB">
<context>
    <name>client</name>
    <message>
        <source>Refresh</source>
        <comment>action name</comment>
        <translation>Refresh</translation>
    </message>
    <message>
        <source>All Measures</source>
        <comment>action name</comment>
        <translation>All Measures</translation>
    </message>
    <message>
        <source>normal</source>
        <translation>normal</translation>
    </message>
   </name>
 </context>
</TS>
Ich bekomme alles bis zum Source-Tag ausgelesen allerdings weiss ich nicht wie ich die anderen Tags auslese ich habe schon versucht mit nextSibling() da rumzuwerkeln aber die Ausgabe die ich mit QDebug<tagName()> erstelle bleibt immer <source>.

und hier nochmal mein Code fals er benötigt wird.

Hier ist mein Aufruf.

Code: Alles auswählen

  
     QFile xmlFile(targetPath);

    xmlFile.open(QIODevice::ReadOnly);

    QByteArray xmlData(xmlFile.readAll());

     myDoc.setContent(xmlData);

    QDomElement root = doc.documentElement();

    QDomNode node = root.firstChild();
    while(!node.isNull())
    {
        if(node.toElement().tagName() == "context")
        {
            parseEntry(node.toElement());
            node = node.nextSibling();
        }
    }

Parseklasse.

Code: Alles auswählen

void MainWindow::parseEntry(const QDomElement &element)
{
    QDomNode node = element.firstChild();
    while(!node.isNull())
    {
        if(node.toElement().tagName() == "name"){
            QDomNode childNode = node.firstChild();
            while(!childNode.isNull())
            {
                if(childNode.nodeType() == QDomNode::TextNode)
                {
                    QDomNode underChild = childNode.firstChild();
                    QString stringChild = underChild.toElement().tagName();
                }
                childNode = childNode.nextSibling();
            }
        }else if(node.toElement().tagName() == "message")
        {
            QDomNode childNode = node.firstChild();
            while(!childNode.isNull())
            {
                if(childNode.nodeType() == QDomNode::TextNode)
                {
                    QDomNode underChild = childNode.firstChild();
                    QString stringChild = underChild.toElement().tagName();
                }
                childNode = childNode.nextSibling();
            }
        }
        node = node.nextSibling();
    }
}
Vielen dank für eure Zeit.
lg Necropsy
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: QDomDocument Strukturparser

Beitrag von Christian81 »

Arbeite mit QDomNode::firstChildElement ( const QString & tagName = QString() ) anstatt über alle Nodes zu iterieren. Dann kommst Du ganz schnell dahin wo du hin willst.
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

Also ich hab es damit ausprobiert aber die Ausgabe ist trotzdem leer bzw es kommt nichts :/
eventuell wäre ne kleine Erklärung oder ein Beispiel hilfreich.

lg Necropsy
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

Okay das funktioniert soweit aber ich weiss nicht wie ich in den nächste <message> tag komme.
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: QDomDocument Strukturparser

Beitrag von Christian81 »

Steht doch in der Beschreibung von firstChildElement() ... nextSiblingElement()
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

wie hab ich das den anzuwenden?
root.firstChild().nextSibling();

oder?

QDomNode child = root.firstChild();
child.nextSibling();

oder?

QDomNode child = root.firstChild();
child = child.nextSibling();
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

Also ich komme in den ersten Message-Tag

Element ist der root den ich aus dem QDomDocument herausziehe.
die Variablen mit actually am Anfang in ihren namen sind am alle 0 zu Beginn.

Code: Alles auswählen

    QDomNode node = element.firstChild();
    QDomNodeList tempNodeList = element.childNodes();
    int nodeCount = tempNodeList.count();

    while(actuallyNodeContext < nodeCount)
    {
        if(node.hasChildNodes())
        {
            QDomNodeList tempNodeChildList = node.childNodes();
            int nodeChildCount = tempNodeChildList.count();

            while(actuallyChildContextNode < nodeChildCount)
            {
                if(actuallyChildContextNode < 1)
                {
                    QDomNode nameChild = node.firstChildElement("name");

                    qDebug()<<nameChild.firstChild().toText().data();

                    nameChild.clear();
                }else{
                    QDomNode messageChild = node.firstChildElement("message");

                    qDebug()<<messageChild.firstChild().toElement().tagName()<<"line: "<<messageChild.firstChild().toElement().attribute("line");

                    messageChild.clear();
                    messageChild = node.firstChildElement("message").nextSibling();
                    qDebug()<<messageChild.toElement().tagName();
                }
                actuallyChildContextNode++;
            }
        }else{
            node = node.nextSibling();
        }
        node = node.nextSibling();
        actuallyChildContextNode = 0;
        actuallyNodeContext++;
    }
}
Der name wird richtig herausgefilter und er bekommt den erste message-tag allerdings, bekomm ich unter den Message tag immer das selbe attribute von "line" (immer von dem ersten Location).

und hier ist der Knackpunkt wo ich es einfach nicht schaffe das nächste Unterelement zb location oder source auszulesen.
ausserdem bekomm ich es auch nicht hin zwischen den message tags zu wechseln.

Code: Alles auswählen

    <message>
        <location filename="pfad_1" line="2142"/>
        <source>Refresh</source>
        <comment>action name</comment>
        <translation>Refresh</translation>
    </message>
    <message>
        <location filename="pfad_2" line="2149"/>
        <source>All Measures</source>
        <comment>action name</comment>
        <translation>All Measures</translation>
    </message>
    <message>
        <location filename="pfad_3" line="2162"/>
        <source>normal</source>
        <translation>normal</translation>
    </message>
Christian81
Beiträge: 7319
Registriert: 26. August 2004 14:11
Wohnort: Bremen
Kontaktdaten:

Re: QDomDocument Strukturparser

Beitrag von Christian81 »

Warum benutzt Du nicht einfach die Funktionen die ich gesagt habe?
Angenommen domRoot ist <context>

Code: Alles auswählen

QDomElement name = domRoot.firstChildElement("name");
QDomElement msg1 = domRoot.firstChildElement("message");
QDomElement msg2 = msg1.nextSiblingElement("message");
...
MfG Christian

'Funktioniert nicht' ist keine Fehlerbeschreibung
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

Entschuldigung ich bin etwas verwirrt zeitweilen durch mein eigenes gescripte xD aber danke nochmal für deine Hilfe, ich denke ich bekomm das nun hin.
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

Ich habe noch eine Frage.

Wie bekomme ich <?xml version="1.0" encoding="utf-8"?> und <!DOCTYPE TS> als Elemente?

Ich hab echt keine Ahnung und es wäre toll wenn mir jemand ein kurzes Beispiel postet.

Ich erstelle ein QByteArray womit ich das file auslese und dan setze ich das QDomDocument damit.

Code: Alles auswählen

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE TS>
<TS version="2.0" language="en_US" sourcelanguage="en_GB">
<context>
    <name>client</name>
    <message>
        <source>Refresh</source>
        <comment>action name</comment>
        <translation>Refresh</translation>
    </message>
   </name>
 </context>
</TS>
lg Necropsy
Necropsy
Beiträge: 14
Registriert: 17. September 2012 09:10

Re: QDomDocument Strukturparser

Beitrag von Necropsy »

Hatt sich erledigt.

Ich bin nun durch mit dem Thema danke an Christian81 für seine Geduld.

lg Necropsy
Antworten