Я столкнулся с той же проблемой в C ++ 11, где действительно ::std::set<T>::iterator
является константой и, следовательно, не позволяет изменять его содержимое, даже если мы знаем, что преобразование не повлияет на инвариант <
. Вы можете обойти это, обернув ::std::set
в тип mutable_set
или написать оболочку для содержимого:
template <typename T>
struct MutableWrapper {
mutable T data;
MutableWrapper(T const& data) : data(data) {}
MutableWrapper(T&& data) : data(data) {}
MutableWrapper const& operator=(T const& data) { this->data = data; }
operator T&() const { return data; }
T* operator->() const { return &data; }
friend bool operator<(MutableWrapper const& a, MutableWrapper const& b) {
return a.data < b.data;
}
friend bool operator==(MutableWrapper const& a, MutableWrapper const& b) {
return a.data == b.data;
}
friend bool operator!=(MutableWrapper const& a, MutableWrapper const& b) {
return a.data != b.data;
}
};
Я считаю, что это намного проще, и это работает в 90% случаев, когда пользователь даже не замечает, что есть что-то между набором и фактическим типом.