2013-08-29 84 views
2

RapidXML是用于在C++中解析XML的可用库之一。为了获取数值,我们可以使用类似于:如何使用rapidxml读取Unicode XML值

node->first_node("xmlnode")->value() 

此命令返回一个char *数据类型。有没有什么方法可以将值作为Unicode读取,以便我可以将其分配给WCHAR或wstring变量?

+0

你找到答案吗?我陷入了同样的问题。 –

回答

1

From the manual

RapidXml是字符类型无关,并且可以与窄的和宽的字符工作两者。当前版本并不完全支持UTF-16或UTF-32,所以使用宽字符有点无能为力。但是,如果数据的字节顺序与机器的字节顺序匹配,它应该成功解析包含UTF-16或UTF-32的wchar_t字符串。

,所以我只是使用以下命令:

#include <rapidxml/rapidxml.hpp> 
typedef rapidxml::xml_node<wchar_t> const *  xml_node_cptr; 
typedef rapidxml::xml_node<wchar_t> *   xml_node_ptr; 
typedef rapidxml::xml_attribute<wchar_t> const * xml_attribute_cptr; 
typedef rapidxml::xml_attribute<wchar_t> *  xml_attribute_ptr; 
typedef rapidxml::xml_document<wchar_t>   xml_doc; 

请注意,如果你这样做,所有参数都将wchar_t的,所以调用first_node()也需要wchar_t的。即

node->first_node(L"xmlnode")->value() 
-1

另一种解决方案是使用中给出的函数:http://msmvps.com/blogs/gdicanio/archive/2010/01/04/conversion-between-unicode-utf-16-and-utf-8-in-c-win32.aspx

CStringW ConvertUTF8ToUTF16(__in const CHAR * pszTextUTF8) 
{ 
    // 
    // Special case of NULL or empty input string 
    // 
    if ((pszTextUTF8 == NULL) || (*pszTextUTF8 == '\0')) 
    { 
     // Return empty string 
     return L""; 
    } 


    // 
    // Consider CHAR's count corresponding to total input string length, 
    // including end-of-string (\0) character 
    // 
    const size_t cchUTF8Max = INT_MAX - 1; 
    size_t cchUTF8; 
    HRESULT hr = ::StringCchLengthA(pszTextUTF8, cchUTF8Max, &cchUTF8); 
    if (FAILED(hr)) 
    { 
     AtlThrow(hr); 
    } 

    // Consider also terminating \0 
    ++cchUTF8; 

    // Convert to 'int' for use with MultiByteToWideChar API 
    int cbUTF8 = static_cast<int>(cchUTF8); 


    // 
    // Get size of destination UTF-16 buffer, in WCHAR's 
    // 
    int cchUTF16 = ::MultiByteToWideChar(
     CP_UTF8,    // convert from UTF-8 
     MB_ERR_INVALID_CHARS, // error on invalid chars 
     pszTextUTF8,   // source UTF-8 string 
     cbUTF8,     // total length of source UTF-8 string, 
           // in CHAR's (= bytes), including end-of-string \0 
     NULL,     // unused - no conversion done in this step 
     0      // request size of destination buffer, in WCHAR's 
     ); 
    ATLASSERT(cchUTF16 != 0); 
    if (cchUTF16 == 0) 
    { 
     AtlThrowLastWin32(); 
    } 


    // 
    // Allocate destination buffer to store UTF-16 string 
    // 
    CStringW strUTF16; 
    WCHAR * pszUTF16 = strUTF16.GetBuffer(cchUTF16); 

    // 
    // Do the conversion from UTF-8 to UTF-16 
    // 
    int result = ::MultiByteToWideChar(
     CP_UTF8,    // convert from UTF-8 
     MB_ERR_INVALID_CHARS, // error on invalid chars 
     pszTextUTF8,   // source UTF-8 string 
     cbUTF8,     // total length of source UTF-8 string, 
           // in CHAR's (= bytes), including end-of-string \0 
     pszUTF16,    // destination buffer 
     cchUTF16    // size of destination buffer, in WCHAR's 
     ); 
    ATLASSERT(result != 0); 
    if (result == 0) 
    { 
     AtlThrowLastWin32(); 
    } 

    // Release internal CString buffer 
    strUTF16.ReleaseBuffer(); 

    // Return resulting UTF16 string 
    return strUTF16; 
} 
+0

尽管这个链接可能回答这个问题,但最好在这里包含答案的基本部分,并提供参考链接。如果链接页面更改,则仅链接答案可能会失效。 –

+0

谢谢Franz,我编辑了包含代码的答案。 – Ali

0

在这里你需要转换到海峡WSTR。 你可以使用这个非标准STD

#include <string> 
#include <codecvt> 
std::wstring_convert<std::codecvt_utf8_utf16<wchar_t>> converter 

std::string strSample; // convert str to wstr 
std::wstring wstrValue = converter.from_bytes(strSample); 

std::wstring wstrSample; // convert wstr to str 
std::string strValue = converter.to_bytes(wstrSample); 

希望这有助于