【问题标题】:Updating a XML file using Qt DOM使用 Qt DOM 更新 XML 文件
【发布时间】:2012-03-21 12:33:20
【问题描述】:

我有一个基于树 Qt 组件构建左侧菜单的应用程序。为了加载它,我需要解析一个 XML 文件。 XML 文件如下所示:

<comandos>
        <categoria>
                <nome>Cupom fiscal</nome>
                <comando>
                        <nome>01 - Abrir Cupom Fiscal</nome>
                        <env>3</env>
                        <rec>4</rec>
                        <desc>CNPJ / CPF : </desc>
                        <desc>Nome : </desc>
                        <desc>Endereco: </desc>
                </comando>
        </categoria>
</comandos>

我实际上可以使用 QtDOM 读取这个 XML。

    QDomDocument doc( "ComandosML" );

    QFile file( "comandos.xml" );

    int r = 0;

    datafields.clear();
    receFields.clear();
    categories.clear();

    if( !file.open( QIODevice::ReadOnly ) )
      return -1;

    if( !doc.setContent( &file ) )
    {
      file.close();
      return -2;
    }

    // Ok we are ready to parse DOM
    QDomElement root = doc.documentElement();
    if( root.tagName() != "comandos" )
      return -3;

    QDomNode n = root.firstChild();
    while( !n.isNull() )
    {
          QDomElement e = n.toElement();
          if( !e.isNull() )
          {
            if( e.tagName() == "categoria" )
            {
                QDomNode cat = n.firstChild();
                while( !cat.isNull() )
                {
                    QDomElement CatName = cat.toElement();

                    if ( CatName.tagName() == "nome")
                    {
                        QString s = CatName.text();

                        if ( s != "")
                        {
                            categories.push_back(s);
                            item = new QStandardItem( (s) );
                            item->setEditable(false);
                        }
                    }

                    if ( CatName.tagName() == "comando")
                    {

                        QDomNode params = cat.firstChild();
                        QString qdCmd;
                        int env = 0;
                        int rec = 0;
                        Categories Desc;

                        while ( !params.isNull())
                        {
                           QDomElement ParamName = params.toElement();

                           if ( ParamName.tagName() == "nome")
                           {
                               qdCmd = ParamName.text();
                               child = new QStandardItem( (qdCmd) );
                               child->setEditable( false );
                               child->setDragEnabled(false);
                               item->appendRow( child );
                           }
                           else
                           if ( ParamName.tagName() == "env")
                           {
                               env = ParamName.text().toInt();
                           }
                           else
                           if ( ParamName.tagName() == "rec")
                           {
                               rec = ParamName.text().toInt();
                           }
                           else
                           if ( ParamName.tagName() == "desc")
                           {
                               Desc.push_back(ParamName.text());
                           }

                           params = params.nextSibling();
                        }

                        datafields.insert(pair<QString,int>(     qdCmd,      env    ));
                        receFields.insert(pair<QString,int>(     qdCmd,      rec    ));
                        descriptions.insert(pair<QString, Categories>( qdCmd, Desc) );
                    }
                    cat= cat.nextSibling();
                }
                model->setItem(r++,item);
            }
          }
          n = n.nextSibling();
    }

    file.close();

    return 0;

在解析之间我已经组装了菜单。毕竟,当用户编辑 xml 文件并在应用程序中重新加载时,我已经为更新 XML 做好了所有设置,我只需擦除树并重新创建它。你可以看到我也将一些数据传递到一些结构上,它们基本上是std::vector和std::map。上面的代码是用 Qt 文档中的示例编写的,顺便说一下,这些示例相当不错。

碰巧我写了一个简单的对话框来让用户避免编辑 XML。好的,对我来说,即使从用户的角度来编辑 XML 可能更容易和更简单,但可能的用户会更喜欢在对话框上编辑内容。这一切都好。我可以抓取数据并将其传递给应用程序。一点问题都没有。

但我需要更新 XML。基本上,编辑将包括通过添加新节点或将子节点插入 under 来更新节点。如何更新节点?有什么具体的方法可以做到这一点吗?我的 XML 经验很短,我通常编写、更新、解析 txt 和二进制文件。

我想做这样的事情:

   if( root.tagName() != "comandos" )
      return -3;

    QDomNode n = root.firstChild();
    while( !n.isNull() )
    {
          QDomElement e = n.toElement();
          if( !e.isNull() )
          {
            if( e.tagName() == "categoria" )
            {
                QDomNode cat = n.firstChild();
                while( !cat.isNull() )
                {

                    QDomElement CatName = cat.toElement();

                    if ( CatName.tagName() == "nome")
                    {
                        QString s = CatName.text();

                        if ( s != qsCategory )
                        {
                            // we have not found the category
                            // add it here

                        }
                        else
                        {
                           // the category exists simply update
                        }



                    }

                    cat= cat.nextSibling();
                }
            }
          }
          n = n.nextSibling();
    }

似乎使用 Qt Dom 来解析和创建 XML 文件相当不错,但是它缺少更新工具。任何帮助都将不胜感激,甚至是一个例子。

这里的另一个线程,看起来很有用

Edit Value of a QDomElement?

我在 Internet 上查看了可以更新 XML 文件的示例。似乎如果我抓住了当前节点,我可以向它添加一个子节点,到目前为止我还没有弄清楚该怎么做。

感谢您的帮助,很抱歉我的无知。

【问题讨论】:

  • 除了您提到的答案之外,您还想要什么?
  • 嗨,我想更新节点。例如,用户将键入类别、命令和其他数据,这需要在 XML 中进行更新。我没有找到如何插入新节点,但基于以前存在的。

标签: xml qt dom


【解决方案1】:

QDomElement newCategoriaTag = doc.createElement(QString("categoria")); 
QDomElement newNomeTag = doc.createElement(QString("nome")); 
QDomText newNomeText = doc.createTextNode(QString("Cupom fiscal 2"));
newNomeTag.appendChild(newNomeText);
newCategoriaTag.appendChild(newNomeTag);
root.appendChild(newCategoriaTag);

这将导致:

<comandos>
        <categoria>
                <nome>Cupom fiscal</nome>
                <comando>
                        <nome>01 - Abrir Cupom Fiscal</nome>
                        <env>3</env>
                        <rec>4</rec>
                        <desc>CNPJ / CPF : </desc>
                        <desc>Nome : </desc>
                        <desc>Endereco: </desc>
                </comando>
        </categoria>
        <categoria>
                <nome>Cupom fiscal 2</nome>
        </categoria>
</comandos>

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-03-17
    • 1970-01-01
    • 2015-12-11
    • 1970-01-01
    • 2021-12-31
    • 2012-01-02
    相关资源
    最近更新 更多