I'd like to start by saying that yes, I Google'd this problem before coming here, and none of the answers seemed relevant.
I stole the below code from What's the best way to trim std::string?, because for whatever reason, there is no standard c++ trim
function. Using Visual Studio, it compiled fine, and I managed to complete the rest of the project without it giving me any errors.
This morning though, I decided to try compiling the entire project manually (using g++ -std=c++11 *.cpp
), and now suddenly the trim
functions are yielding the following error:
DVD.cpp: In static member function 'static DVD DVD::parseDVD(std::string, std::string)':
DVD.cpp:65:59: error: invalid initialization of non-const reference of type 'std::string& {aka std::basic_string<char>&}
from an rvalue of type 'std::basic_string<char>'
std::string rID = trim(dataStr.substr(0, preTitlePos - 1));
It yields similar errors for the other 2 times that trim
is used.
Here is the "stolen" code:
(Utils.h):
static inline std::string& ltrim(std::string& s) {
s.erase(s.begin(), std::find_if(s.begin(), s.end(), std::not1(std::ptr_fun<int, int>(std::isspace))));
return s;
}
// trim from end
static inline std::string& rtrim(std::string& s) {
s.erase(std::find_if(s.rbegin(), s.rend(), std::not1(std::ptr_fun<int, int>(std::isspace))).base(), s.end());
return s;
}
// trim from both ends
static inline std::string& trim(std::string& s) {
return ltrim(rtrim(s));
}
And here is the parseDVD
function that the error mentions:
(DVD.cpp):
DVD DVD::parseDVD(std::string dataStr, std::string delimiter) {
DVD newDVD;
int preTitlePos = dataStr.find(delimiter, 0);
int preGenrePos = dataStr.find(delimiter, preTitlePos + 1);
// V Error is here V
std::string rID = trim(dataStr.substr(0, preTitlePos - 1));
std::string rTitle = trim(dataStr.substr(preTitlePos + 1, preGenrePos - preTitlePos - 1));
std::string rGenre = trim(dataStr.substr(preGenrePos + 1));
int parsedID = 0;
//Requirements for a successful parse
//The ID must be fully numeric, and both of the delimiters must have been found
if (parseInt(rID, parsedID) && preTitlePos > -1 && preGenrePos > -1) {
return
newDVD .setID(parsedID)
.setTitle(rTitle)
.setGenre(rGenre);
}
return badDVD;
}
If I remove all of the &
s from the trim functions, it works, but I'd rather it not make copies constantly.
This baffles me because I know the code is sound; not only is it the accepted answer to the above question, but it works fine in Visual Studio.