QtXml

Alles rund um die Programmierung mit Qt
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

QtXml

Beitrag von stonecold »

Hallo habe folgenden Beispielcode:

Code: Alles auswählen

// imports
#include <iostream>
#include <string>
#include <Qt/qfile.h>
#include <Qt/qstring.h>
#include <QtXml/QDomDocument>
#include <QtXml/QDomElement>
#include <QtXml/QDomNode>

int main( int argc, char* argv[] )
{
	QDomDocument doc("exercise");
	QFile file("myxml.xml");
	if (!file.open(QIODevice::ReadOnly))
	{
		std::cout << "Error: file couldn't be opened !" << std::endl;
		return 1;
	}
	if (!doc.setContent(&file)) 
	{
		file.close();
		std::cout << "Error: content couldn't set !" << std::endl;
		return 1;
	}

	QDomElement docElem = doc.documentElement();
	QDomNode n = docElem.firstChild();
	while(!n.isNull()) 
	{
		QDomElement e = n.toElement(); // try to convert the node to an element.
		if(!e.isNull()) 
		{
			std::cout << e.tagName().toStdString() << std::endl;
		}
		n = n.nextSibling();
	}
	file.close();
	system("pause");
 return 0;
}
Warum bekomme ich beim Einlesen des folgendem XML-File (aus Forum):

Code: Alles auswählen

<?xml version="1.0"?>
<Konfiguration> 
  <Sektion> 
    <Name>MalerInfos</Name> 
    <Kommentar>Informationen für Maler</Kommentar> 
    <InfoSet> 
      <Info> 
        <Einheit>Blau</Einheit> 
        <Datum>01.01.2007</Datum> 
        <Beschreibung>Alles gruen machen</Beschreibung> 
      </Info> 
    </InfoSet> 
  </Sektion> 
</Konfiguration>
derartige Ausgaben:

Code: Alles auswählen

`¡@ Sektion ïi@ øi@    ☼   ëFA
±BÓ ‼ `¡@ "╚ȶ    ­ ‼ Îoü|Ó0+┼Z½Ã☺ ░²⌂8®TÇ╚ ‼ ɸÅé    ►Üâ|Óoü|            AN@     Actx    ☺   ÿ$
        ☻               ¶☻  £☺      [IY-░♥  2   õ♥  Ê☻      õ☻☻â©♠  F      Û☻      ÊıîÐý
  ♦♥  ►   ♦   È   ☻   ☺   ¶☺  î☼  ☺   ☻   á►  ,♥  ☺   ♦   ╠‼  P►  ☻   ♠   ∟$  |   ☻   SsHd,   ☺
                    ☻   $   4   C : \ W I N D O W S \ W i n S x s \                  ☺  £☺  ☺   [I
F         Û☻  ♦   .¡jÏ♀♀  F   T♀  ♦♥  ♣   d   ☺
......u.s.w.

Liegt mein Problem vielleicht hier?

Code: Alles auswählen

 e.tagName().toStdString()
Mein Ziel ist es ein über DTD definiertes XML-File zu öffnen und mit Hilfe einer GUI zu bearbeiten. Fange nun erstmal mit dem Öffnen an (divide et impera). Was muss ich beachten ( allgemein und bezüglich DTD )? Besteht die Möglichkeit das XML-File mit Hilfe der DTD auf Korrektheit zu überprüfen. Gibt es ggf. schon Beispiele?

Danke und Gruß!
Volker
Beiträge: 343
Registriert: 30. Juni 2005 05:27

Beitrag von Volker »

Soweit ich weiss kann cout kein std::string verarbeiten. Also entweder versuchst du's mit .c_str() oder mit qDebug(qPrintable( QString Variable ))
Bitte seid so nett und ändert den Titel von Beiträgen die gelöst wurden, auf [gelöst] Beitragstitel
dhcase
Beiträge: 132
Registriert: 10. Juni 2006 20:38

Beitrag von dhcase »

oder e.tagName().toAscii().constData(), obwohl ich auch eher qDebug() benutzen würde
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

Beitrag von stonecold »

Das mit dem std::string geht, d.h. std::cout funzt mit string.
Wollte eure Bsp. ausprobieren. Welche/s include/s brauche ich dafür?
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

Beitrag von stonecold »

So das

Code: Alles auswählen

e.tagName().toAscii().constData()
funktioniert, liefert allerdings nur das zweite Element "Sektion". WARUM? Was genau muss ich machen um qDebug bzw. qPrintable benutzen zu können?
Volker
Beiträge: 343
Registriert: 30. Juni 2005 05:27

Beitrag von Volker »

Eigentlich nichts. Da du ja bereits QT Dateien inkludierst, sollte qDebug und qPrintable zur Verfügung stehen.

Sektion wird ausgegeben, da es das erste Kind des Dokumentknotens ist und keine weiteren "Geschwister" hat.
Bitte seid so nett und ändert den Titel von Beiträgen die gelöst wurden, auf [gelöst] Beitragstitel
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

Beitrag von stonecold »

Okay...habe ich gerade gesehen. Wie nur, komme ich aber an die darunterliegenden Elemente?

Dein Beispiel mit qDebug kann doch aber so nicht funktionieren oder?

Code: Alles auswählen

qDubug(qPrintable( "qString" ))
Das funktioniert:

Code: Alles auswählen

qPrintable( "qString" )
Wozu qDebug?
Volker
Beiträge: 343
Registriert: 30. Juni 2005 05:27

Beitrag von Volker »

Bzgl. der Kinder kannst Du z.B. eine rekursive Funktion verwenden.

Bzgl. qDebug und qPrintable
http://doc.trolltech.com/4.3/qtglobal.html#qPrintable
http://doc.trolltech.com/4.3/qtglobal.html#qDebug
Bitte seid so nett und ändert den Titel von Beiträgen die gelöst wurden, auf [gelöst] Beitragstitel
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

Beitrag von stonecold »

Danke erstmal für die Antworten. Nun habe ich aber noch zwei Fragen. Wozu brauche ich QDomNode?

Z.B.

Code: Alles auswählen

QDomElement docElem = doc.documentElement();
	qDebug(qPrintable(docElem.tagName()));
	
	QDomNode n = docElem.firstChild();

	while(!n.isNull()) 
	{
		QDomElement e = n.toElement(); 
		if(!e.isNull()) 
(aus Beispiel Doku)

erst DomElement, dann DomNode und dann wieder Element??? Warum bleibe ich nicht bei Element? Warum überhaupt DomNode?
Und wie komme ich bitte in meiner Struktur weiter nach unten, wenn ich nicht nur die firstChilds haben will?
Volker
Beiträge: 343
Registriert: 30. Juni 2005 05:27

Beitrag von Volker »

Nicht jedes Kind ist ein Element (z.B. Attribute). Wenn Du ein Unterelement haben willst, kannst du auch statt firstChild, firstChildElement nehmen, das liefert dir gleich ein QDomElement (analog nextSiblingElement).

Bzgl. der nächsten Ebene hab ich Dir schonmal geantwortet, benutze eine rekursive Funktion.
Bitte seid so nett und ändert den Titel von Beiträgen die gelöst wurden, auf [gelöst] Beitragstitel
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

Beitrag von stonecold »

Okay diesen Rat hatte ich bereits berücksichtigt.

Code: Alles auswählen

void getAll( const QDomElement& m, int i )
{
	qDebug("%d: %s", i, qPrintable(m.tagName()));
	if(m.hasChildNodes())
	{
		i = i*10; // wie soll ich sonst die Ebene erkennen?
		QDomElement n = m.firstChildElement();
		while(!n.isNull())
		{
			getAll( n, i );
			n = n.nextSiblingElement();
		}
	}
}
So weit, so gut! Nun möchte ich die XML-Struktur gerne in einem QTreeWidget abbilden (später auch ändern) [Natürlich muss ich auch Attr etc. berücksichtigen, das mache ich aber dann später]. Gibt es bereits entsprechende Hilfen von Trolltech? Bzw. vielleicht Beispielcode von wem anders?
upsala
Beiträge: 3946
Registriert: 5. Februar 2006 20:52
Wohnort: Landshut
Kontaktdaten:

Beitrag von upsala »

Schon mal in den Beispielen geschaut, die bei der Doku dabei sind?
Volker
Beiträge: 343
Registriert: 30. Juni 2005 05:27

Beitrag von Volker »

Bitte seid so nett und ändert den Titel von Beiträgen die gelöst wurden, auf [gelöst] Beitragstitel
stonecold
Beiträge: 147
Registriert: 19. Oktober 2005 10:48

Beitrag von stonecold »

Versuche gerade das Beispiel aus dem Link zu übersetzten. (An dieser Stelle noch mal danke dafür). Nach einigen Änderungen bleibt folgendes über:

Code: Alles auswählen

dommodel.obj : error LNK2001: Nichtaufgeloestes externes Symbol "public: virtual int __thiscall DomModel::qt_metacall(enum QMetaObject::Call,int,void * *)" (?qt_metacall@DomModel@@UAEHW4Call@QMetaObject@@HPAPAX@Z)
dommodel.obj : error LNK2001: Nichtaufgeloestes externes Symbol "public: virtual void * __thiscall DomModel::qt_metacast(char const *)" (?qt_metacast@DomModel@@UAEPAXPBD@Z)
dommodel.obj : error LNK2001: Nichtaufgeloestes externes Symbol "public: virtual struct QMetaObject const * __thiscall DomModel::metaObject(void)const " (?metaObject@DomModel@@UBEPBUQMetaObject@@XZ)
dommodel.obj : error LNK2001: Nichtaufgeloestes externes Symbol "public: static struct QMetaObject const DomModel::staticMetaObject" (?staticMetaObject@DomModel@@2UQMetaObject@@B)
Debug/Qt_Projekt.exe : fatal error LNK1120: 4 unaufgeloeste externe Verweise
Was mache ich falsch? Und noch viel wichtiger, woher wisst ihr, was ich falsch mache?
Volker
Beiträge: 343
Registriert: 30. Juni 2005 05:27

Beitrag von Volker »

Wie die Fehlermeldung sagt, kann der Linker die Implementierungen zu qt_metacall, qt_metacast, metaObject und staticMetaObject von DomModel nicht finden. Wie schon des öfteren in diesem Forum beantwortet, werden diese Methoden vom MO'Compiler erstellt. D.h bei dir fehlt diese MOC Datei beim linken.
Bitte seid so nett und ändert den Titel von Beiträgen die gelöst wurden, auf [gelöst] Beitragstitel
Antworten