找了好久,很遗憾的发现wxWidget没有提供很好的XML文件解析类,只好自己写一个了,主要用来获取xml节点及读取节点的值,已经够自己用了。废话不多说,直接上代码了。
头文件:
#ifndef WXXMLHELPER_H #define WXXMLHELPER_H #pragma once #include <wx/xml/xml.h> #include <wx/list.h> class wxXmlHelper { public: wxXmlHelper(void); ~wxXmlHelper(void); /** * @brief 加载XML文件. * @param sFilePath [in]文件路径. * @return True or False. * @remarks * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ bool Load(const wxString sFilePath); /** * @brief 获取xml节点的内容. * @param sXPath [in]节点路径. * @return Content of node or empty string for Failed. * @code wxXmlHelper h; h.Load("Order.xml"); wxString s = h.GetContent("/Order/InputParameter/Mod4FilePath"); * @endcode * @remarks * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxString GetContent(const wxString sXPath); /** * @brief 获取xml节点的内容. * @param pNode [in]搜索起始节点. * @param sXPath [in]节点路径. * @code wxXmlHelper h; h.Load("Order.xml"); wxString s = h.GetContent(h.GetRoot(),"/Order/InputParameter/InputFile"); * @endcode * @return Content of node or empty string for Failed. * @remarks sXPath使用"/"分隔各节点的名称,并且应该包含当前节点的名称. * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxString GetContent(wxXmlNode *pNode,wxString sXPath); /** * @brief 获取xml节点的内容. * @param sXPath [in]节点路径. * @param sProName [in]属性名称. * @return Property of node or empty string for Failed. * @code wxXmlHelper h; h.Load("Order.xml"); s = h.GetProperty("/Order/InputParameter/InputFile","id"); * @endcode * @remarks sXPath使用"/"分隔各节点的名称,并且应该包含当前节点的名称. * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxString GetProperty(const wxString sXPath,const wxString sProName); /** * @brief 获取xml节点的内容. * @param pNode [in]搜索起始节点. * @param sXPath [in]节点路径. * @param sProName [in]属性名称. * @code wxXmlHelper h; h.Load("Order.xml"); wxString s = h.GetProperty(h.GetRoot(),"/Order/InputParameter/InputFile","id"); * @endcode * @return Property of node or empty string for Failed. * @remarks sXPath使用"/"分隔各节点的名称,并且应该包含当前节点的名称. * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxString GetProperty(wxXmlNode *pNode,wxString sXPath,const wxString sProName); /** * @brief 获取xml文档的根节点. * @return Node or Null for Failed. * @remarks * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxXmlNode *GetRoot(); /** * @brief 获取xml节点. * @param pNode [in]搜索起始节点. * @param sXPath [in]节点路径. * @return Node or Null for Failed. * @code wxXmlHelper h; h.Load("Order.xml"); wxXmlNode* node = h.GetNode(h.GetRoot(),"/Order/InputParameter/InputFile"); * @endcode * @remarks sXPath使用"/"分隔各节点的名称,并且应该包含当前节点的名称. * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxXmlNode *GetNode(wxXmlNode *pNode,wxString sXPath); /** * @brief 查找制定路径下的所有节点. * @param pNode [in]搜索起始节点. * @param sXPath [in]节点路径. * @remarks Use like this: * @code wxXmlHelper h; h.Load("Order.xml"); wxList *lst = h.GetNodes(h.GetRoot(),"/Order/InputParameter/InputFile"); wxList::iterator it = lst->begin(),end = lst->end(); while(it!=end) { wxXmlNode *node = (wxXmlNode*)(*it); wxString s = node->GetName(); wxPrintf(_T("name = %s id = %s \n"),s,node->GetPropVal("id","")); ++it; } delete lst; // //Or use wxList::compatibility_iterator it = lst->GetFirst(); while(it) { wxXmlNode *node = (wxXmlNode*)(it->GetData()); wxString s = node->GetName(); wxPrintf(_T("name = %s id = %s \n"),"")); it = it->GetNext(); } * @endcode * @author Zhengwen.Fu * @history - 1.Created by Zhengwen.Fu on 25th Mar,2015. */ wxList *GetNodes(wxXmlNode *pNode,wxString sXPath); private: wxXmlDocument m_Doc; }; #endif源文件:
#include "wxXmlHelper.h" #include <wx/arrstr.h> #include <wx/dynarray.h> wxXmlHelper::wxXmlHelper(void) { } wxXmlHelper::~wxXmlHelper(void) { } bool wxXmlHelper::Load(const wxString sFilePath) { return m_Doc.Load(sFilePath); } wxString wxXmlHelper::GetContent(const wxString sXPath) { return GetContent(m_Doc.GetRoot(),sXPath); } wxString wxXmlHelper::GetContent(wxXmlNode *pNode,wxString sXPath) { wxXmlNode *node = GetNode(pNode,sXPath); if(node) return node->GetChildren()->GetContent(); else return ""; } wxString wxXmlHelper::GetProperty(const wxString sXPath,const wxString sProName) { return GetProperty(m_Doc.GetRoot(),sXPath,sProName); } wxString wxXmlHelper::GetProperty(wxXmlNode *pNode,const wxString sProName) { wxXmlNode *node = GetNode(pNode,sXPath); if(node) return node->GetPropVal(sProName,""); else return ""; } wxXmlNode *wxXmlHelper::GetRoot() { return m_Doc.GetRoot(); } wxXmlNode *wxXmlHelper::GetNode(wxXmlNode *pNode,wxString sXPath) { if(!pNode) return NULL; int pos = sXPath.Find("/"); if(pos==0) { sXPath = sXPath.substr(1); return GetNode(pNode,sXPath); } if(pos==wxString::npos) { if (pNode->GetName()==sXPath) return pNode; else return GetNode(pNode->GetNext(),sXPath); } wxString s = sXPath.substr(0,pos); sXPath = sXPath.substr(pos+1); while(pNode && pNode->GetName() != s) pNode = pNode->GetNext(); return GetNode(pNode->GetChildren(),sXPath); } wxList *wxXmlHelper::GetNodes(wxXmlNode *pNode,wxString sXPath) { wxList *list = new wxList(); int pos = sXPath.find_last_of(_T('/')); wxString sName = sXPath.substr(pos+1); wxXmlNode *node = GetNode(pNode,sXPath); while(node) { if(node->GetName()==sName) list->Append(reinterpret_cast<wxObject*>(node)); node = node->GetNext(); } return list; }下面是试验时用到的xml文件:
<?xml version="1.0" encoding="utf-8"?> <Order> <InputParameter> <InputFile id="001">../testdata/input/20070512_TM_rad.img</InputFile> <InputFile id="002">../testdata/input/20070512_TM_rad.img</InputFile> <InputFile id="003">../testdata/input/20070512_TM_rad.img</InputFile> <InputFile id="004">../testdata/input/20070512_TM_rad.img</InputFile> <Mod4FilePath>../testdata/input/Mod4.hdf</Mod4FilePath> </InputParameter> <OutputParameter> <OutputFile>../testdata/output/20070512_TM_Ref.img</OutputFile> </OutputParameter> </Order>