2009-10-12 103 views
2

我已經嘗試了以下代碼與正常的ifstreams和當前的boost:我使用的iostream,都有相同的結果。C++ c_str不返回整個字符串

它旨在從physfs加載文件到內存中,然後將其傳遞給處理程序來處理(例如圖像,音頻或數據)。目前,當調用c_str時,它只返回文件的一小部分。

 PhysFS::FileStream file("Resources/test.png" , PhysFS::OM_READ); 

    if(file.is_open()) { 

     String* theFile; 

     theFile = new String((std::istreambuf_iterator<char>(file)), 
     std::istreambuf_iterator<char>()); 

     String::iterator it; 
     for (it=theFile->begin() ; it < theFile->end(); it++) { 
      std::cout << *it; 
     } // Outputs the entire file 

     std::cout << theFile->c_str(); // Outputs only the first few lines 

    } 

該迭代循環輸出作爲預期整個PNG文件,但c_str調用僅返回前幾個字符(\ 211PNG)。

我一直在嘗試此代碼的變體很長時間沒有成功。有任何想法嗎?

回答

15

我想象下一個字符是空(ASCII 0)字節。 c_str()只是給你一個* char,因此你寫到標準輸出被解釋爲一個以第一個空字節結尾的C類字符串。

如果你確實需要類似C的接口,這個字符串最重要的是,文件 - > c_str()指向你的數據,而文件長度爲你提供字符串中的字符數。所以你可能想要做這樣的事情:

char *c_value = theFile->c_str() 
for (int i = 0; i < theFile.length; i++) 
{ 
    cout << c_value[i]; 
} 

真正的解決方案取決於你爲什麼要首先轉換爲char *。如果您正在調用只接受char *的遺留函數,那麼該遺留函數可能還有一個長度參數。

+0

我該如何解決這個問題?我對C風格字符串沒有太多經驗 – 2009-10-12 16:59:58

+0

不要使用c_str() - 使用std :: string操作 – Mark 2009-10-12 17:07:04

+0

我正在使用需要c字符串輸入的庫。 – 2009-10-12 17:09:37

2

一個字節的可能是0.這意味着字符串的結尾來清點傳遞一個char *(這c_str是)

2

我會考慮使用std::vector<unsigned char>代替std::string這個時候。處理矢量中的二進制數據要容易得多。如果您需要訪問C型陣列,則可以使用&vec[0]引用基礎指針。我也會確保你的文件抽象使用std::ios_base::binary作爲引擎蓋下的文件模式。

+0

關於在輸入上設置二進制模式非常好的一點。 – catfood 2009-10-12 17:40:00

+0

據我所知,在PhysFS中無法以二進制模式打開文件。缺乏關於如何使用PhysFS的適當示例是爲什麼我認爲將文件讀入內存而不是顯示問題是一個問題。 :-( – 2009-10-12 18:48:25

+0

)是的,我也會這樣說:不要把整個文件讀入內存,除非我猜你肯定它會很小, – catfood 2009-10-12 19:35:39

相關問題