Модераторы: Daevaorn
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> const_iterator в set 
V
    Опции темы
cppGhost
Дата 18.3.2016, 18:50 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 101
Регистрация: 24.4.2013

Репутация: нет
Всего: нет



Доброго времени суток. Понимаю, что отстал лет на пять и в инете вроде говорится, мол, успокойтесь, но вопрос меня мучает. Дело касается const_iterator в set после 11 стандарта.
Зачем так сделали вцелом я понимаю. Но у меня не укладывается в голове, а как в больших проектах теперь быть? Ну то есть ситуация 
Код

class A
{
public:

    A() : _val(int(5))
    {
    }

    int _val;    
};

void main()
{
    std::set<A> arr;
    arr.insert(A());
    arr.insert(A());

    std::set<A>::const_iterator it = arr.begin();
    it->_val = 10;    
}

утрированно, но суть проста: есть сет объектов (чтобы была уникальность массива), пробегаемся по нему и в зависимости от чего-то там меняем какие-то члены обекта "А".
как теперь быть? делать const_cast? переписывать с set на map? оставаться на старом компиляторе? вешаться?)
PM MAIL   Вверх
disputant
Дата 18.3.2016, 21:38 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 210
Регистрация: 28.11.2011

Репутация: нет
Всего: 3



Ну если вы понимаете все - то что вообще за вопрос?
Как вы себе представляете, например, изменение set<int>, в котором вы будете все элементы делать одинаковыми?... Ведь их при этом надо удалять из множества.

Если что-то НЕ СУЩЕСТВЕННОЕ ДЛЯ СРАВНЕНИЯ - то объявите mutable:

Код
class A
{
public:

    A() : _val(int(5))
    {
    }

    bool operator <(const A& a) const { return _val < a._val; }

    int _val;
    mutable int _mal;
};

void main()
{
    std::set<A> arr;
    arr.insert(A());
    arr.insert(A());

    std::set<A>::iterator it = arr.begin();
    it->_mal = 10;
}





Это сообщение отредактировал(а) disputant - 18.3.2016, 21:40
PM MAIL   Вверх
cppGhost
Дата 19.3.2016, 10:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 101
Регистрация: 24.4.2013

Репутация: нет
Всего: нет



Да, я понимаю. НО, если уж я своей компании небольшой столкнулся с этой проблемой, то как же другие огроменные проекты? Или прямо в майкрософте так всё круто, что они никогда не меняли члены данных объектов, лежащих в set. Или у них во всех set'ах находятся только указатели на объекты? Ведь раньше же люди жили)) и никто н ежаловался. Ну то есть наверняка кто-то простреливал себе ногу, но это ж c++
PM MAIL   Вверх
disputant
Дата 19.3.2016, 18:40 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 210
Регистрация: 28.11.2011

Репутация: нет
Всего: 3



Цитата(cppGhost @ 19.3.2016,  10:43)
Да, я понимаю. НО, если уж я своей компании небольшой столкнулся с этой проблемой, то как же другие огроменные проекты? Или прямо в майкрософте так всё круто, что они никогда не меняли члены данных объектов, лежащих в set. Или у них во всех set'ах находятся только указатели на объекты? Ведь раньше же люди жили)) и никто н ежаловался. Ну то есть наверняка кто-то простреливал себе ногу, но это ж c++

Вообще-то я никогда не слышал, что элементы set можно менять. Насколько я знаю - они ВСЕГДА, с самого начала были константными.

Так что о каких таких старых проектах вы говорите - что-то не понимаю. Как и того, во имя чего надо вдруг менять элементы множества...
PM MAIL   Вверх
cppGhost
Дата 19.3.2016, 22:27 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 101
Регистрация: 24.4.2013

Репутация: нет
Всего: нет



Нет, ну постойте. Вот самый обычный случай. Я из БД запрашиваю какие-то элементы. Каждый такой элемент представляет собой экземпляр класса со своим набором данных. Запросов у меня много, могут возвращаться одинаковые объекты. Поэтому я использую set вместо массива для уникализации и простоты. А дальше мне нужно пройтись по этому сету и поменять какие-то свойства этих объектов, ну или для кажлго вызвать какой-нибудь неконстантный метод. И вот раньше это работало, а теперь компиляться не будет. Или вы хотите сказать, что так нормальные программисты не делают? А складывают они все вектор, затем выбрасывают дубли и делай что хочешь. А зачем тогда сет? Чтобы хранить <int> ?

Это сообщение отредактировал(а) cppGhost - 19.3.2016, 22:28
PM MAIL   Вверх
sQu1rr
Дата 20.3.2016, 05:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Опытный
**


Профиль
Группа: Участник
Сообщений: 597
Регистрация: 11.11.2008
Где: london

Репутация: 3
Всего: 13



Цитата(disputant @  19.3.2016,  16:40 Найти цитируемый пост)
Насколько я знаю - они ВСЕГДА, с самого начала были константными

В теории, на практике до с++11 неконстантные итераторы позволяли менять данные. разумеется это не самое разумное занятие - нужно следить что бы не менять сортировочные данные. это был дефект стандарта и его неуспели исправить в с++03, зато исправили в с++11. так что считаем, что действительно, должны были быть константными с самого начала.

В любом случае, если вы используете сет только для уникальных результатов, что вам мешает потом перенести все в вектор, и менять там. или например использовать вектор изначально и хранить список хешей или ИД или чего угодно, что бы не добавлять дубликаты. и разумеется, const_cast вполне легально, если не трогать сортировочные данные, или трогать, но не добавляться и не удалять ничего из сета.
PM MAIL Skype GTalk   Вверх
disputant
Дата 20.3.2016, 08:55 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 210
Регистрация: 28.11.2011

Репутация: нет
Всего: 3



Цитата(sQu1rr @ 20.3.2016,  05:30)
если не трогать сортировочные данные, или трогать, но не добавляться и не удалять ничего из сета.

И не менять местами... 

Для ТС - поскольку отследить такое в общем случае невозможно - лучше этого ничего не делать smile
PM MAIL   Вверх
cppGhost
Дата 20.3.2016, 09:46 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 101
Регистрация: 24.4.2013

Репутация: нет
Всего: нет



Я понял, после 10 лет коммерческого программирования у меня открылись глаза)) 

p.s. странно что сырые указатели не запретили использовать))
PM MAIL   Вверх
disputant
Дата 20.3.2016, 11:05 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 210
Регистрация: 28.11.2011

Репутация: нет
Всего: 3



Цитата(cppGhost @ 20.3.2016,  09:46)
Я понял, после 10 лет коммерческого программирования у меня открылись глаза)) 

Теперь понятно, почему коммерческие программы такого качества  smile 
PM MAIL   Вверх
cppGhost
Дата 20.3.2016, 18:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 101
Регистрация: 24.4.2013

Репутация: нет
Всего: нет



очень политкорректно. что-то я не помню такого совета, например, у майерса в его книжках об stl.
PM MAIL   Вверх
disputant
Дата 20.3.2016, 20:42 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Бывалый
*


Профиль
Группа: Участник
Сообщений: 210
Регистрация: 28.11.2011

Репутация: нет
Всего: 3



Цитата(cppGhost @ 20.3.2016,  18:30)
очень политкорректно. что-то я не помню такого совета, например, у майерса в его книжках об stl.

Политкорректностью не страдаю - не в америке, чай, живем...

Ладно, раз так... "C++ и STL..." Мюссера и компании. У нас издана в 2010, у "них" - в 2001. Стр. 318 нашего издания - функции-члены для обращения к элементам.
begin, end и иже с ними - описаны как "возвращает константный итератор".

Кому-кому, но Мюссеру верить в области STL можно smile

Саттер, "Решение сложных задач на C++", стр. 80 - "будучи вставлен в контейнер, ключ не должен изменять свое значение способом, который может привести к изменению его относительного положения в контейнере".

Там же, стр. 83 - читайте сами, но общий смысл тот же: не надо трогать ключ, а если надо - лучше бы это делалось с предельной осторожностью с использованием const_cast, чтобы никто не мог просто так наменять там такого, что... а потому, в комитет по стандартам внесено предложение требовать, чтобы все итераторы были только константными, чтоб без const_cast никуда... 2002 год.

Хватит пока что? smile

PM MAIL   Вверх
cppGhost
Дата 20.3.2016, 21:04 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Шустрый
*


Профиль
Группа: Участник
Сообщений: 101
Регистрация: 24.4.2013

Репутация: нет
Всего: нет



Снимаю шляпу
PM MAIL   Вверх
xvr
Дата 21.3.2016, 15:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 60
Всего: 223



Цитата(cppGhost @  19.3.2016,  10:43 Найти цитируемый пост)
Или прямо в майкрософте так всё круто, что они никогда не меняли члены данных объектов, лежащих в set.

Наверное меняли, но de-facto set после этого можно считать разрушенным. И что куда продолжит итерировать после такого никто гарантировать не сможет  smile 

Цитата(cppGhost @  19.3.2016,  10:43 Найти цитируемый пост)
Ну то есть наверняка кто-то простреливал себе ногу,

В данном случае скорее голову  smile 

PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "С++:Общие вопросы"
Earnest Daevaorn

Добро пожаловать!

  • Черновик стандарта C++ (за октябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика(4.4мб).
  • Черновик стандарта C (за сентябрь 2005) можно скачать с этого сайта. Прямая ссылка на файл черновика (3.4мб).
  • Прежде чем задать вопрос, прочтите это и/или это!
  • Здесь хранится весь мировой запас ссылок на документы, связанные с C++ :)
  • Не брезгуйте пользоваться тегами [code=cpp][/code].
  • Пожалуйста, не просите написать за вас программы в этом разделе - для этого существует "Центр Помощи".
  • C++ FAQ

Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Earnest Daevaorn

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Общие вопросы | Следующая тема »


 




[ Время генерации скрипта: 0.1605 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.