2010-05-11 157 views
16

我必须用C++解析XML文件。我正在研究并为此找到RapidXml库。如何解析RapidXML中的XML文件

我对doc.parse<0>(xml)有疑问。

可以xml是.xml文件还是它需要是stringchar *

如果只能采取stringchar *那么我想我需要读取整个文件并将其存储在char数组中,并将其指针传递给该函数?

有没有办法直接使用文件,因为我需要更改代码中的XML文件。

如果在RapidXML中不可行,那么请在C++中建议一些其他XML库。

谢谢!

Ashd

+1

xml_document :: parse()的参数是包含xml的以零结尾的字符串。所以你只需要创建一个file2string函数。将文件读入一个向量缓冲区,然后将&buffer [0]传递给parse()。 – anno 2010-05-30 03:04:43

+0

vtd-xml也有C++端口,与rapidXML相比,vtd-xml更符合,稳定和高效...... – 2011-01-02 22:34:36

回答

0

manual告诉我们:

功能xml_document ::解析

[...]根据给定的标志解析零结尾的XML字符串 。

RapidXML让叶片从文件中加载字符数据给你。将文件读入缓冲区,例如建议使用anno,或者使用一些内存映射技术。 (但是请先查看parse_non_destructive标志。)

7

新来C++自己...但我想分享一个解决方案。

YMMV!

喊出SiCrane这个thread: - 而只是一个载体代替“串” ---(感谢安诺)

请评论并帮助我也学习!我很新的这

无论如何,这似乎有一个良好的开始工作:

#include <iostream> 
#include <fstream> 
#include <vector> 

#include "../../rapidxml/rapidxml.hpp" 

using namespace std; 

int main(){ 
    ifstream myfile("sampleconfig.xml"); 
    rapidxml::xml_document<> doc; 

    /* "Read file into vector<char>" See linked thread above*/ 
    vector<char> buffer((istreambuf_iterator<char>(myfile)), istreambuf_iterator<char>()); 

    buffer.push_back('\0'); 

    cout<<&buffer[0]<<endl; /*test the buffer */ 

    doc.parse<0>(&buffer[0]); 

    cout << "Name of my first node is: " << doc.first_node()->name() << "\n"; /*test the xml_document */ 


} 
+0

这很好,但只有'vector buffer'不会超出范围:a快速和肮脏的方式来解决这个问题是通过添加'静态'关键字向量,但我不认为这是真的很干净。 请参阅:http://stackoverflow.com/questions/6363719/rapidxml-reading-from-file-what-is-wrong-here – FlipMcF 2011-07-23 01:45:55

2

我们通常从磁盘读取的XML转换为std::string,建立这样一个安全拷贝成std::vector<char>,如下面所示:

string input_xml; 
string line; 
ifstream in("demo.xml"); 

// read file into input_xml 
while(getline(in,line)) 
    input_xml += line; 

// make a safe-to-modify copy of input_xml 
// (you should never modify the contents of an std::string directly) 
vector<char> xml_copy(input_xml.begin(), input_xml.end()); 
xml_copy.push_back('\0'); 

// only use xml_copy from here on! 
xml_document<> doc; 
// we are choosing to parse the XML declaration 
// parse_no_data_nodes prevents RapidXML from using the somewhat surprising 
// behavior of having both values and data nodes, and having data nodes take 
// precedence over values when printing 
// >>> note that this will skip parsing of CDATA nodes <<< 
doc.parse<parse_declaration_node | parse_no_data_nodes>(&xml_copy[0]); 

对于一个完整的源代码的检查:

Read a line from xml file using C++

+0

由于调整矢量大小,这太慢了。与Superfly Jon的回答相比,它要快得多。 – 2015-05-15 15:54:25

26

RapidXml提供了一个类来为你做这件事,rapidxml::filerapidxml_utils.hpp文件中。 喜欢的东西:

#include "rapidxml_utils.hpp" 

int main() { 
    rapidxml::file<> xmlFile("somefile.xml"); // Default template is char 
    rapidxml::xml_document<> doc; 
    doc.parse<0>(xmlFile.data()); 
... 
} 

注意,xmlFile对象现在包含了所有XML,这意味着,一旦超出范围和被破坏doc变量不再安全使用的数据。如果你在一个函数内部调用分析,你必须以某种方式保留内存中的对象(全局变量,新的等),以便该文档保持有效。