This question already has answers here:
c++ passing a const object reference to a function
(5 answers)
Closed 9 years ago.
stockListType.cpp:58: instantiated from here
/usr/include/c++/4.2.1/bits/stl_algo.h:91: error: passing ‘const stockType’ as ‘this’ argument of ‘bool stockType::operator<(const stockType&)’ discards qualifiers
/usr/include/c++/4.2.1/bits/stl_algo.h:92: error: passing ‘const stockType’ as ‘this’ argument of ‘bool stockType::operator<(const stockType&)’ discards qualifiers
/usr/include/c++/4.2.1/bits/stl_algo.h:94: error: passing ‘const stockType’ as ‘this’ argument of ‘bool stockType::operator<(const stockType&)’ discards qualifiers
/usr/include/c++/4.2.1/bits/stl_algo.h:98: error: passing ‘const stockType’ as ‘this’ argument of ‘bool stockType::operator<(const stockType&)’ discards qualifiers
/usr/include/c++/4.2.1/bits/stl_algo.h:100: error: passing ‘const stockType’ as ‘this’ argument of ‘bool stockType::operator<(const stockType&)’ discards qualifiers
Above is the error I got and would like someone to explain to me what it means. I solved the error by placing a constant in front of the overloading operator. My program was a stock market application that read a file that includes a string, 5 doubles and an int. We sort out the program by the string symbols and the index gain. The book instructed me to use vectors to store each data. As you see below the overload operator compares each symbol and sorts it out using the sort member function of containers. My question is why did I have to put a constant in front of the overload operator for > and <. but not for >=, <=, ==, != overload operators.
//function was declared in stockType.h and implemented in stockType.cpp
bool operator<(const stockType& stock)//symbol is a string
{
return (symbols < stock.symbols)
}
//The function below was defined in stockListType.h and implemented in
// stockListType.cpp where I instantiated the object of stockType as a vector.
//vector<stockType> list; was defined in stockListType.h file
void insert(const& stockType item)
{
list.push_back(item);
}
void stockListType::sortStockSymbols()
{
sort(list.begin(), list.end());
}
The error message tells you that you that you are casting of const from your object in operator< function. You should add const to all member functions that don't modify member.
bool operator<(const stockType& stock) const
// ^^^^^
{
return (symbols < stock.symbols)
}
The reason why compiler complains about operator< is because std::sort uses operator< to compare the elements.
Also you have another syntax error in insert function.
Update:
void insert(const& stockType item);
to:
void insert(const stockType& item);
// ^^
Related
This question already has answers here:
C++ "error: passing 'const std::map<int, std::basic_string<char> >' as 'this' argument of ..."
(3 answers)
Closed 6 years ago.
Fetching an entry from a const C++ std::map fails to compile on gcc 5.4.0.
test_map.cpp: In function ‘int main()’:
test_map.cpp:9:24: error: passing ‘const std::map<int, int>’ as ‘this’ argument discards qualifiers [-fpermissive]
foo[key];
Minimal test case
// Compile with
// g++ test_map.cpp -o test_map
#include <map>
int main() {
const std::map<int, int> foo;
foo[0]; // compiles if "const" above is suppressed
}
Look before you post
This looks similar to passing ‘const this argument discards qualifiers [-fpermissive] which is about a Cache, not a std::map. The cause there: the user calls a write() method. That method is not declared const which makes sense since writing presumably modified the object.
But here, fetching an element from a map does not modify the map, does it?
Question
The actual map in my real use case is indeed const. It's fully initialized in the source code. It does not make sense to modify it. Declaring it non-const practically solves the problem but does not make sense.
operator[] doesn't have a const qualifier in std::map, as you can see from the documentation, e.g. std::map::operator[] - cppreference.com:
Returns a reference to the value that is mapped to a key equivalent to key, performing an insertion if such key does not already exist.
Therefore you cannot use it directly on a const instance. Use at instead (ref std::map::at - cppreference.com) if you can afford C++11 features.
Declarations for those member functions follow:
T& operator[](const key_type& x);
T& operator[](key_type&& x);
T& at(const key_type& x);
const T& at(const key_type& x) const;
I have the following variable in QT:
QVector<QVector <int> > buff_d1;
and I need to modify the "inner" vector:
buff_d1.at(i).removeFirst();
buff_d1.at(i).push_back(d1.at(i).at(sample_number));
this is causing the errors:
passing 'const QVector<int>' as 'this' argument of 'void QVector<T>::removeFirst() [with T = int]' discards qualifiers [-fpermissive] buff_d2.at(i).removeFirst();
passing 'const QVector<int>' as 'this' argument of 'void QVector<T>::push_back(const T&) [with T = int]' discards qualifiers [-fpermissive] buff_d1.at(i).push_back(d1.at(i).at(sample_number));
I understand that the "inner" vector is const so I can't modify it, but what is the work around it?
Your at() function returns a const reference:
const T & QVector::at(int i) const
and you're trying to modify this with the removeFirst() function. You should rather use the [] operator to modify it since it provides a non-const returning overload:
T & QVector::operator[](int i)
The same applies for the second error.
at(int index) member function returns an const reference, see the documentation here, so you need to use operator[int index] to return a non const reference to be able to modify it.
I got a problem with a iterator. When i compile my project i keep getting this error.
Kitchen.cpp: In member function ‘void Kitchen::If_Cook_Ok(const Order&) const’:
Kitchen.cpp:45:33: error: passing ‘const Order’ as ‘this’ argument of ‘std::list<IngredType::Ingredient> Order::getIngredient()’ discards qualifiers [-fpermissive]
Kitchen.cpp:45:70: error: passing ‘const Order’ as ‘this’ argument of ‘std::list<IngredType::Ingredient> Order::getIngredient()’ discards qualifiers [-fpermissive]
I already tried to put constness on the function member, but i keep getting this error. Here is the code
The Order class has as member variable a std::list witch is returned by the getter getIngredients()
void Kitchen::If_Cook_Ok(const Order &order) const
{
std::cout << "congratulations you barely made it" << std::endl;
std::list<IngredType::Ingredient>::const_iterator it;
for (it = order.getIngredient().begin(); it != order.getIngredient().end(); ++it)
{
std::cout << *it << std::endl;
}
}
Help will be much appreciated.
order is a const Order&. Thus, you could only call const methods of Order class. And it appears that Order::getIngredient() is not const.
TheOrder parameter in the method If_Cook_Ok is const, so you can only call const methods on this object. Perhaps the getIngredients() method is not const. Try adding const on that method.
I am trying to sort a vector of objects. I have written a function to compare the objects. It seems to work fine on my compiler but not the one my school's server has.
bool sortByLastName(Student& lhs, Student& rhs) {
string lhsLastName = lhs.getLastName();
string rhsLastName = rhs.getLastName();
return lhsLastName < rhsLastName;
}
I get this error...
/usr/lib/gcc/i686-redhat-linux/4.4.7/../../../../include/c++/4.4.7/bits/stl_algo.h:131: error: invalid initialization of reference of type ‘Student&’ from expression of type ‘const Student’
/usr/lib/gcc/i686-redhat-linux/4.4.7/../../../../include/c++/4.4.7/bits/stl_algo.h:133: error: invalid initialization of reference of type ‘Student&’ from expression of type ‘const Student’
I tried to make the arguments const String& but that also resulted in this error...
Lab9Roster.cpp:79: error: passing ‘const Student’ as ‘this’ argument of ‘std::string Student::getLastName()’ discards qualifiers
Lab9Roster.cpp:80: error: passing ‘const Student’ as ‘this’ argument of ‘std::string Student::getLastName()’ discards qualifiers
Define getLastName as
string getLastName() const;
and return
return lhs.getLastName() < rhs.getLastName();
I am sure you are passing temporary parameters like sortByLastName("s1", "s2"). However, though I doubt if it would work on some compilers, mostly non-const references don't bind to temporary objects.
Use
bool sortByLastName(const Student& lhs,const Student& rhs) {
string lhsLastName = lhs.getLastName();
string rhsLastName = rhs.getLastName();
return lhsLastName < rhsLastName;
}
Also, as #user3435400 has mentioned, define getLastName() as const, that is it cannot modify any class members
string getLastName() const;
I am trying to create a custom sort for a vector of class pointers by using a sort predicate:
struct sort_by_airtime
{
inline bool operator() (const Network *n1, const Network *n2)
{
return (n1->airtime() < n2->airtime());
}
};
For each network, we sort by a float returned by airtime().
Now, I try to use this as follows:
std::vector<Network *> Simulator::sort_networks(std::vector<Network *> netlist, bool sort_airtime) {
std::vector<Network *> new_netlist = netlist;
if(sort_airtime) {
sort(new_netlist.begin(), new_netlist.end(), sort_by_airtime());
}
}
However, I get a lot of errors like this:
In file included from Simulator.cpp:7:
Simulator.h: In member function ‘bool Simulator::sort_by_airtime::operator()(const Network*, const Network*)’:
Simulator.h:48: error: passing ‘const Network’ as ‘this’ argument of ‘virtual float Network::airtime()’ discards qualifiers
Simulator.h:48: error: passing ‘const Network’ as ‘this’ argument of ‘virtual float Network::airtime()’ discards qualifiers
Am I not specifying the argument passed to the predicate properly? airtime() is implemented by classes that inherit the Network class.
The compiler is warning you that Network::airtime() is ignoring the const qualifiers on n1 and n2.
The solution would be to create a "const-correct" version of Network::airtime() (assuming it actually doesn't modify anything).
See this answer for an example.
Your member function should be declared as const member function as:
virtual float Network::airtime() const
^^^^^ //this makes the function const
because the pointers which you're using in operator() are pointing to const objects of type Network.
Network::airtime() is not const, and so can't be called via the const Network* you have in sort_by_airtime.
If possible, the best solution is to make airtime() const; otherwise change the sort_by_airtime arguments to Network*.