#include <iostream>
#include <set>
using namespace std;
class StudentT {
public:
int id;
string name;
public:
StudentT(int _id, string _name) : id(_id), name(_name) {
}
int getId() {
return id;
}
string getName() {
return name;
}
};
inline bool operator< (StudentT s1, StudentT s2) {
return s1.getId() < s2.getId();
}
int main() {
set<StudentT> st;
StudentT s1(0, "Tom");
StudentT s2(1, "Tim");
st.insert(s1);
st.insert(s2);
set<StudentT> :: iterator itr;
for (itr = st.begin(); itr != st.end(); itr++) {
cout << itr->getId() << " " << itr->getName() << endl;
}
return 0;
}
В линию:
cout << itr->getId() << " " << itr->getName() << endl;
Это дает ошибку, которая:
../main.cpp:35: ошибка: передача 'const StudentT' в качестве аргумента 'this' для int StudentT :: getId () 'отменяет квалификаторы
../main.cpp:35: ошибка: передача 'const StudentT' в качестве 'this' аргумента 'std :: string StudentT :: getName ()' отменяет квалификаторы
Что не так с этим кодом? Спасибо!
volatile
Ответы:
Объекты в
std::set
хранятся какconst StudentT
. Поэтому , когда вы пытаетесь вызватьgetId()
сconst
объектом компилятор обнаруживает проблему, главным образом , вы вызываете неконстантную функцию - член константный объект , который не допускается , поскольку неконстантные функции - члены сделать NO PROMISE не изменять объект; поэтому компилятор сделает безопасное предположение, котороеgetId()
может попытаться изменить объект, но в то же время он также заметит, что объект является const; поэтому любая попытка изменить объект const должна быть ошибкой. Следовательно, компилятор генерирует сообщение об ошибке.Решение простое: сделать функции такими же:
Это необходимо, потому что теперь вы можете вызывать
getId()
иgetName()
const объекты как:В качестве обозначения, вы должны реализовать
operator<
как:Примечание параметры теперь
const
ссылки.источник
const StudentT & s1, const StudentT & s2
?const
потому что функция не нуждается в изменении объекта, поэтомуconst
обеспечивает выполнение этого во время компиляции.Функции-члены, которые не изменяют экземпляр класса, должны быть объявлены как
const
:Каждый раз, когда вы видите «отбрасывает квалификаторы», это говорит о
const
илиvolatile
.источник
const
он приходит, но я подозреваю, чтоset
он возвращает ссылку на const от итератора, чтобы предотвратить изменение экземпляра и, таким образом, сделать набор недействительным.foo obj;
наconst foo obj;
один раз и посмотрите, что произойдет. Или передайтеconst
ссылку наfoo
.set
изменены, порядок может быть нарушен, и тогда набор больше не действителен. Вmap
, только ключ естьconst
. В целомset
, весь объект действительно является ключом.f()
в моем ответе.На самом деле стандарт C ++ (то есть черновик C ++ 0x ) гласит (tnx to @Xeo & @Ben Voigt за указание на это мне):
Таким образом, реализация Dinkumware в VC ++ 2008 неисправна.
Старый ответ:
Вы получили эту ошибку, потому что в некоторых реализациях библиотеки std то
set::iterator
же самое, что иset::const_iterator
.Например, libstdc ++ (поставляется с g ++) имеет его (см. Здесь весь исходный код):
И в документах SGI говорится:
С другой стороны, VC ++ 2008 Express компилирует ваш код, не жалуясь на то, что вы вызываете неконстантные методы в
set::iterator
s.источник
Позвольте мне привести более подробный пример. Что касается структуры ниже:
Как вы видите выше, IDE (CLion) даст подсказки
Non-const function 'getCount' is called on the const object
. В методеadd
count
объявлен как const объект, но методgetCount
не является методом const, поэтомуcount.getCount()
может изменять члены вcount
.Ошибка компиляции, как показано ниже (основное сообщение в моем компиляторе):
Чтобы решить вышеуказанную проблему, вы можете:
uint32_t getCount(){...}
наuint32_t getCount() const {...}
. Такcount.getCount()
что не буду менять членовcount
.или
uint32_t add(const Count& count){...}
наuint32_t add(Count& count){...}
. Такcount
что не волнуйтесь о смене членов в нем.Что касается вас проблем, объекты в станде :: набор сохраняется как константа StudentT, но метод
getId
иgetName
не сопзИте, поэтому вы даете вышеуказанную ошибку.Вы также можете увидеть этот вопрос Значение 'const' последний в объявлении функции класса? для более подробной информации.
источник