#c #object #pointers #reference
Вопрос:
У меня есть класс, который выглядит примерно так:
Пример.h:
class Example{
private:
int m_x, m_y;
public:
void print_params() const;
void modify_params();
};
Example.cpp:
void Example::print_params() const{
cout << "x: "<< m_x << ", y: " << m_y << endl;
}
void Example::modify_params(){
m_x = 1;
m_y = 1;
}
В моем основном файле у меня есть несколько std::set
Example
объектов. Затем я повторяю набор и вызываю modify_params()
функцию для каждого Example
объекта, чтобы изменить частные переменные каждого объекта. Следовательно, код в основном файле выглядит примерно так:
set<Example> example_set;
...
for (autoamp; example: example_set){
example.modify_params();
}
Однако это не компилируется, и я получаю следующую ошибку:
«этот» аргумент функции-члена «modify_params» имеет тип «Пример const», но функция не помечена как const.
Нигде в объявлении класса я не объявлял его как const
, и я не могу пометить modify_params()
функцию как const
, цель этой функции-изменить частные переменные. Имейте в виду, что у меня нет проблем с вызовом print_params()
метода в том виде, в каком он отмечен const
.
Что я здесь упускаю? Как я могу успешно делать то, что я пытаюсь сделать?
Комментарии:
1. Объекты в списке
std::set
являются постоянными и не поддаются изменению.2. Удалите объект из набора, измените объект, вставьте измененный объект обратно в набор.
3. … и для повышения эффективности, если вы используете C 17 или более позднюю версию, используйте
std::set::extract
, а затем измените и переместите его обратно вset
.4. Чтобы увидеть , кто виноват
std::set
, измените используемый кодstd::vector<Example> example_set;
.5. Да, в этом есть смысл. Я буду иметь это в виду, продолжая работать над своим кодом. Спасибо!
Ответ №1:
Здесь просто некоторая теоретическая основа. Вы должны помнить, что std::set
это реализовано в виде двоичного дерева, поэтому то, где элемент вставляется в дерево, зависит от его значения и от значения элементов, которые уже находятся в дереве, это определяется во время вставки каждого элемента.
Это двоичное дерево построено таким образом, что элементы могут быть извлечены и вставлены в отсортированном порядке с производительностью журнала(n). Изменение значения одного элемента в дереве приведет к нарушению порядка.
Вот почему в этом случае вам следует либо удалить и повторно вставить измененный элемент std::set
, либо использовать другой контейнер, такой как std::vector
или std::list
.
Комментарии:
1. Да! Спасибо, что указали на это! Я совершенно забыл, что множества неизменны. Мой код отлично работает, когда я меняю набор на вектор!