2013-10-29 13 views
0

我有一個數組是這樣的:如何從XML獲得字符串中的COM

static WCHAR FilesToShow[][100] = { { L"start.cmd" },{ L"image.xml" }, { L"xyz" }}; 

,你看到有「XYZ」我有一些獨特的名稱來代替。爲此,我必須讀取image.xml文件。

請你能告訴我該怎麼做。

我寫了這樣的方法:

PRIVATE WCHAR GetSystemName(WCHAR *pName) 

{ 
    WCHAR line; 

    wfstream in("image.xml"); 
    WCHAR tmp; 

    bool begin_tag = false; 
    while (getline(in,line)) 
    { 
     // strip whitespaces from the beginning 
     for (int i = 0; i < line.length(); i++) 
     { 
      if (line[i] == ' ' && tmp.size() == 0) 
      { 
      } 
      else 
      { 
       tmp += line[i]; 
      } 
     }   

     if (wcswcs(tmp,"<SystemPath>") != NULL) 
     {  
      ???????? how to get "vikash" from here <SystemPath>C:\Users\rs_user\Documents\RobotStudio\Systems\vikash</SystemPath> 
     } 
     else 
     { 
      continue; 
     } 

    } 

    return tmp; 
} 

我得到wfstream,函數getline和line.length()方法例外。 我已經包含fstream.h頭文件,但我認爲它不支持在COM中。

請幫助我如何解決這個問題,而無需解析XML文件。

+0

在上述問題我已經從與vikash或任何動態值陣列替換 「XYZ」。 – user2932395

回答

0

如果您的XML文件是很簡單的,這樣只有具有指定名稱的一個標籤,你可以做這樣的:

#include <string> 
#include <sstream> 
#include <iostream> 

std::wstring get_value(std::wistream & in, std::wstring const & tagname) 
{ 
    std::wstring text = std::wstring(std::istreambuf_iterator<std::wstring::value_type>(in), 
            std::istreambuf_iterator<std::wstring::value_type>()); 

    std::wstring start_tag = L"<" + tagname + L">"; 
    std::wstring end_tag = L"</" + tagname + L">"; 

    std::wstring::size_type start = text.find(start_tag); 
    if (start == std::wstring::npos) 
    { 
    throw 123; 
    } 
    start += start_tag.length(); 

    std::wstring::size_type end = text.find(end_tag); 
    if (end == std::wstring::npos) 
    { 
    throw 123; 
    } 
    return text.substr(start, end - start); 
} 

std::wstring get_substr_after(std::wstring const & str, wchar_t delim) 
{ 
    std::wstring::size_type pos = str.rfind(delim); 
    if (pos == std::wstring::npos) 
    { 
    throw 123; 
    } 
    return str.substr(pos + 1); 
} 


void stackoverflow() 
{ 
    std::wstring text(L"<foo>\n<bar>abc/def/ghi</bar>\n<baz>123/456/789</baz>\n</foo>\n"); 
    std::wistringstream wiss(text); 

    std::wcout << text << std::endl; 
    std::wcout << get_substr_after(get_value(wiss, std::wstring(L"bar")), L'/') << std::endl; 

} 

這個程序的輸出是:

<foo> 
<bar>abc/def/ghi</bar> 
<baz>123/456/789</baz> 
</foo> 

ghi 

我希望能回答你的問題。

0

這裏有幾個問題。

  1. 你做了什麼是編譯器錯誤,而不是例外
  2. 頭文件,包括是「fstream的」而不是「fstream.h」。
  3. 確保你有一個行說using namespace std;
  4. 您聲明lineWCHAR類型的變量,所以它是一個寬字符,這肯定不是一個wstring對象。因此line.length()不正確。
  5. 你爲什麼要混合使用C(wcswcs())和C++(STL)?也許你應該重新設計你的功能簽名。

但是,請嘗試以下功能。我修改了簽名以返回指向WCHAR的指針,並將請求的字符串放在由pName提供的緩衝區空間中。我添加了一個檢查來驗證緩衝區足夠大以適應名稱和終止NULL字符。

WCHAR* GetSystemName(WCHAR *pName, size_t buflen) 
{ 
    wstring line; 
    wifstream in("image.xml"); 
    WCHAR* tmp = NULL; 

    while (getline(in,line)) 
    { 
     // strip whitespaces from the beginning 
     size_t beg_non_whitespace = line.find_first_not_of(L" \t"); 
     if (beg_non_whitespace != wstring::npos) 
     { 
      line = line.substr(beg_non_whitespace); 
     } 

     size_t beg_system_path = line.find(L"<SystemPath>"); 
     if (beg_system_path != wstring::npos) 
     {  
      // strip the tags (assuming closing tag is present) 
      size_t beg_data = beg_system_path + wstring(L"<SystemPath>").length(); 
      size_t range = line.find(L"</SystemPath>") - beg_data; 
      line = line.substr(beg_data, range); 

      // get file name 
      size_t pos_last_backslash = line.find_last_of(L'\\'); 

      if (pos_last_backslash != wstring::npos) 
      { 
       line = line.substr(pos_last_backslash + 1); 

       if (buflen <= line.length()) 
       { 
        // ERROR: pName buffer is not large enough to fit the string + terminating NULL character. 
        return NULL; 
       } 

       wcscpy(pName, line.c_str()); 
       tmp = pName; 
       break; 
      } 
     } 
    } 

    return tmp; 
} 

編輯:此外,如果你正在使用和/或在你的程序的其他區域解析XML,我強烈建議使用XML解析庫如Xerces-ClibXml2

0

謝謝大家的回答。在這裏我解決了我的問題。

PRIVATE WCHAR * GetNewSystemName() {

WCHAR line[756]; 
    WCHAR tempBuffer[100]; 

CComBSTR path = CurrentFolder.Path(); 

CComBSTR imagePath1 = L"rimageinfo.xml"; 


path.AppendBSTR(imagePath1); 



    std::wfstream in(path); 



WCHAR tmp[756]; 



in.getline(line, 756); 

WCHAR* buffer; 



buffer = wcswcs(line, L"<SystemPath>"); 
WCHAR *dest = wcsstr(buffer, L"</SystemPath>"); 
    int pos; 
    pos = dest - buffer; 
unsigned int i = 0; 
if (wcswcs(buffer,L"<SystemPath>") != NULL && wcswcs(buffer,L"</SystemPath>") != NULL) 
{ 
    for (; i < pos; i++) 
    { 
     if (buffer[i] == ' ' && sizeof(tmp) == 0) 
     { 
     } 
     else 
     { 
      tmp[i] = buffer[i]; 

     } 
    } 

    tmp[i] = NULL; 
    //break; 
} 

int j = i; 

for (; j > 0; j--) 
{ 
    if (tmp[j] == '\\') 
    { 

     break; 
    } 
} 

j++;  
int k = 0; 
for (; j < i ; j++) 
{ 
    System_Name[k] = tmp[j]; 
    k++; 
} 

System_Name[k] = NULL; 
    return System_Name;