2015-02-10 159 views
2

我正在使用std :: stringstream來構造一個字符串,然後嘗試傳遞完成的字符串作爲一個函數的參考,它需要一個參數std ::字符串&。從std :: stringstream傳遞std :: string參數作爲參數

我在GCC得到一個編譯錯誤:

../src/so.cpp:22:21: error: invalid initialization of non-const reference of type ‘std::string& {aka std::basic_string<char>&}’ from an rvalue of type ‘std::basic_stringstream<char>::__string_type {aka std::basic_string<char>}’ 
../src/so.cpp:12:6: error: in passing argument 1 of ‘void myFunc(std::string&)’ 
make: *** [src/so.o] Error 1 

相同的代碼在Windows VS2012編譯,但無法在我的Linux和Android版本。這是什麼原因?

我可以通過暫時將ss.str()分配給一個臨時std :: string,然後通過引用傳遞該字符串來解決此問題,但這看起來有點愚蠢。乾淨地做這件事的正確方法是什麼?

#include <iostream> 
#include <sstream> 

void myFunc (std::string& msg) 
{ 
    std::cout << msg << std::endl; 
} 

int main (void) 
{ 
    std::stringstream ss; 
    ss << "this is a test"; 

    myFunc (ss.str());    // Fails 

    std::string s = ss.str(); 
    myFunc (s);      // Pass 

    return 0; 
} 
+1

將警告等級設置爲'/ W4',VS會告訴你在該線路上正在使用非標準的分機。 – Praetorian 2015-02-10 21:05:15

回答

4

的問題是,myFunc需要一個非-const左值引用。 stringstream::str()按值返回一個字符串。你不能將標準C++中的臨時變量綁定到一個非const的左值引用,但是VS有一個允許這樣做的「擴展」。這就是編譯VS的原因,而不是其他編譯器。

const左值引用另一方面可以綁定到右值。因此,從而改變你的函數會使其工作:

void myFunc (const std::string &msg) { /* as before */ } 
+0

非常感謝您的訣竅;說得通。感謝您的其他答案,但是我發現這是最具信息量的。 – Chris 2015-02-10 21:09:50

1

既然你不是裏面myFunc寫入字符串,接受const引用:

void myFunc (std::string const &msg) 
{ 
    std::cout << msg << std::endl; 
} 

那些可以綁定到臨時對象

3

更改此:

void myFunc (std::string& msg) 

這樣:

void myFunc (const std::string& msg) 
//   ^^^^^ this will allow temporaries like ss.str() 

有Visual Studio中的版本,將愚蠢允許臨時綁定到非const引用。但是,它是危險且無效的C++

-1

所以你有這個錯誤的原因是ss.str()返回一個常量字符串,而不是一個字符串。 通過創建一個新的字符串,您正在創建一個非常量變量,它被設置爲與ss.str()相同的值,因此可以傳遞到myFunc()中。 製作一個新的字符串,因爲你有它可能是最簡單的方法來解決這個問題,仍然使用該功能。

+0

但'ss.str()'不返回一個常量字符串。 – juanchopanza 2015-02-10 21:13:04

相關問題