c++ - RapidXML 属性值错误

标签 c++ xml rapidxml

我过去使用 RapidXML 时遇到了几个问题,但这个问题让我很困惑。

我正在创建应用程序事件时间戳的日志,外部程序可以在重播中读取在正确时间发生在原始应用程序中的任何音频。

在应用程序初始化时,会正确生成以下 XML:

<?xml version="1.0" encoding="utf-8"?>
<playbacklog>
    <logitem type="general" event="start" timestamp="85639323"/>
</playbacklog>

一旦添加了下一项,文档就会变成这样:

<?xml version="1.0" encoding="utf-8"?>
<playbacklog>
    <logitem type="general" event="start" timestamp="NUL NUL NUL NUL"/>
    <logitem type="audio" event="start" timestamp="86473833">
</playbacklog>

然后:

<?xml version="1.0" encoding="utf-8"?>
<playbacklog>
    <logitem type="general" event="start" timestamp="@NUL NUL' NUL NUL"/>
    <logitem type="audio" event="start" timestamp="NUL NUL NUL NUL">
    <logitem type="audio" event="stop" timestamp="8654533">
</playbacklog>

随着每个新的 startstop 对的添加,还可以看到最终的以下行为,所有节点的时间戳值都发生了变化事件属性值:

<?xml version="1.0" encoding="utf-8"?>
<playbacklog>
    <logitem type="general" event="start" timestamp="@NUL NUL' NUL NUL"/>
    <logitem type="audio" event="start" timestamp="NUL NUL NUL NUL">
    <logitem type="audio" event="stop" timestamp="8674519">
    <logitem type="audio" event="start" timestamp="NUL NUL NUL NUL">
    <logitem type="audio" event="stop" timestamp="8674519">
    <logitem type="audio" event="start" timestamp="NUL NUL NUL NUL">
    <logitem type="audio" event="stop" timestamp="8674519">
</playbacklog>

我在 C++ 头文件中这样声明文档:

private:
    rapidxml::xml_document<> outputDocument;

为了创建每个节点,我使用了以下代码:

// tStamp is a typedef'd std::pair containing two std::string values, one for the
// time at which the evet occurred and the other containing the event type.
void AudioLogger::LogEvent( Timestamp* tStamp )
{
    rapidxml::xml_node<>* nodeToAdd = outputDocument.allocate_node(rapidxml::node_element, "logitem");
    ...
    nodeToAdd->append_attirbute(outputDocument.allocate_attribute("timestamp", ts->first.c_str()));
    ...

    outputDocument.first_node()->next_sibling()->append_node(nodeToAdd);
}

传递给此函数的 TimeStamp* 值保存在 std::vector 中,当添加新值时,将调用此函数。

如果有人对这里发生的事情有任何想法,那将是一个巨大的帮助。另外,如果需要更多信息,我也可以提供。

最佳答案

这是一个经典的 RapidXML“陷阱”。每当您将 char 指针传递给 RapidXML 时,它只是存储指针而不是复制字符串。它被清楚地记录在案,但仍然经常让人们感到困惑。 http://rapidxml.sourceforge.net/manual.html#namespacerapidxml_1modifying_dom_tree

答案是像这样使用 allocate_string 函数:

 nodeToAdd->append_attribute(outputDocument.allocate_attribute("timestamp", 
                             outputDocument.allocate_string(ts->first.c_str()))); 

(您不需要在 allocate_string 中包装“timestamp”,因为它是文字,所以不会改变)。

我通常使用自己的辅助包装器 - 像这样:-

class MyRapidXmlDoc : public rapidxml::xml_document<char>
{
...
  Attribute* allocateAttribute(const string &name, const string &value = "")
  {
    if (value.empty())
      return allocate_attribute(allocate_string(name.c_str()));
    else
      return allocate_attribute(allocate_string(name.c_str()), allocate_string(value.c_str()));
  }

关于c++ - RapidXML 属性值错误,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/20970205/

相关文章:

C++,无法实例化抽象类错误

xml - 在 XML 中连接来自多个节点的值 - 使用 XSLT

c++ - RapidXML 节点在 try catch block 中具有正确的值,但它在 block 外为 nullptr

c++ - 错误处理 : distinguishing between 'fatal' errors and 'unexpected input' errors

c++ - RapidXML是否支持xml :space ="preserve"?

c++ - 关于更改返回类型 C++ 的二进制兼容

c++ - std::condition_variable 的 notify_all() 和 notify_one() 有什么区别?

javascript - 无法使用 angularjs 将 json 数据绑定(bind)到表

python - 我想解析 xml 数据并将其作为 mysql 查询进行处理

c++ - 如何从基类构造函数调用派生类虚方法?