C++之error: cannot bind non-const lvalue reference of type ‘myString’ to an rvalue of type ‘myString
先看代碼(不想看代碼可以直接看代碼后的問題描述)
| 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 | //header.h #ifndef _HEADER_H #define _HEADER_H #define defaultSize 128 #include<iostream> #include<string.h> using?namespace?std; class?myString { ????private: ????????char?*ch; ????????int?curLength; ????????int?maxSize; ????public: ????????myString(int?sz=defaultSize); ????????myString(const?char?*init); ????????myString(const?myString& ob); ????????~myString(){delete?[]ch;} ????????void?print(); ????????int?Length()const; ????????myString operator()(int?pos,?int?len); ????????myString& operator = (myString& ob); }; myString& myString::operator = (myString& ob) { ????if(&ob!=this) ????{ ????????delete[]ch; ? ????????this->ch =?new?char[ob.maxSize]; ????????this->maxSize = ob.curLength; ????????strcpy(this->ch, ob.ch); ????????this->curLength = ob.curLength; ????} ????else ????{ ????????cerr<<"String copy error\n"; ????} ????return?*this; } ? myString myString::operator()(int?pos,?int?len) { ????myString temp; ????if(pos<0 || len<=0 || pos+len-1>=this->maxSize) ????{ ????????temp.curLength = 0; ????????temp.ch[0] =?'\0'; ????} ????else ????{ ????????if(pos+len-1 >=?this->curLength) ????????????len =?this->curLength-pos; ????????temp.curLength = len; ????????for(int?i=0,j=pos; i<len; ++i,++j) ????????????temp.ch[i] =?this->ch[j]; ????????temp.ch[len] =?'\0'; ????} ????return?temp; } ? int?myString::Length()const { ????return?this->curLength; } ? void?myString::print() { ????cout<<this->ch<<endl; } ? myString::myString(int?sz) { ????this->maxSize = sz; ????this->ch =?new?char[this->maxSize+1]; ????if(this->ch == NULL) ????{ ????????cerr<<"Allocation ERROR\n"; ????????exit(1); ????} ????this->curLength = 0; ????ch[0] =?'\0'; } ? myString::myString(const?char?*init) { ????int?len =?strlen(init); ????this->maxSize = (len > defaultSize) ? len : defaultSize; ????this->ch =?new?char[this->maxSize+1]; ????if(this->ch == NULL) ????{ ????????cerr<<"Application Memory ERROR\n"; ????????exit(1); ????} ? ????this->curLength = len; ????strcpy(this->ch, init); ? } ? myString::myString(const?myString& ob) { ????this->maxSize = ob.maxSize; ????this->ch =?new?char[this->maxSize+1]; ????if(this->ch == NULL) ????{ ????????cerr<<"Application Memory ERROR\n"; ????????exit(1); ????} ????this->curLength = ob.curLength; ????strcpy(this->ch, ob.ch); ? } ? #endif |
?
| 1 2 3 4 5 6 7 8 9 10 11 12 | //main.cpp #include"header.h" ? int?main() { ????myString st(10), st1("ABCDEFG"); ????myString st2(st1); ????st.print(), st1.print(), st2.print(); ????st = st1(0, 4);//??? ????st.print(); ????return?0; } |
這是一個字符串類,問題出現在了兩個符號重載,()和=
()重載是想對字符串對象做一個切片,返回一個臨時對象,=重載就不用說了,就是賦值。
問題就出現在總是無法將這個切片后的臨時對象賦值給等號前的對象,編譯后如下:
?
?
?
在網上一番查找后找到一個類似問題
https://blog.csdn.net/u011068702/article/details/64443949
也就是說,在st1(0,4)時存在了一個臨時變量,當把這個臨時變量傳給st時,由于在=重載函數聲明中,參數為myString&,而并不是常量引用。
這個錯誤是C++編譯器的一個關于語義的限制。
如果一個參數是以非const引用傳入,c++編譯器就有理由認為程序員會在函數中修改這個值,并且這個被修改的引用在函數返回后要發揮作用。但如果你把一個臨時變量當作非const引用參數傳進來,由于臨時變量的特殊性,程序員并不能操作臨時變量,而且臨時變量隨時可能被釋放掉,所以,一般說來,修改一個臨時變量是毫無意義的,據此,c++編譯器加入了臨時變量不能作為非const引用的這個語義限制。
?
了解這個語義以后就簡單了,只需給=重載參數加上const常量限制符。
(類中=重載函數聲明也別忘了要加上const)
加上以后程序的運行結果
?
可以,很正確。
總結:
c++中臨時變量不能作為非const的引用參數
2019/12/14更新
最近看到一個類似問題,即C++11
?
| 1 2 3 | int?i=0; ++++i;//這樣是可以的 i++++;//這樣就是錯誤的 |
?
?我們知道前++就是直接對對象自增后返回對象,而后++會先返回記錄當前值,在自增,最后返回一個無名的臨時對象,那么 i++++就是讓第一個后++返回的無名臨時對象再自增,這樣對C++是無意義的,所以這樣就無法編譯通過。//ps.這就是常說的 舉一隅以三隅反 吧
不積小流無以成江河
總結
以上是生活随笔為你收集整理的C++之error: cannot bind non-const lvalue reference of type ‘myString’ to an rvalue of type ‘myString的全部內容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 计算机网络:05---网络类型:局域网、
- 下一篇: C++ 类的隐式转换