Как изменить элементы QSet?

Я имею QSet<QuadPattern> texture; и я хотел бы изменить все QuadPattern в цикле.

foreach это не хорошее решение, потому что оно делает копию.

С этим кодом:

QMutableSetIterator<QuadPattern>  it(texture);
while (it.hasNext())
{
    it.next();
    it.value().setCoordinate(...));
}

Я получаю ошибку компиляции:

error: C2662: 'QuadPattern::setCoordinate' : cannot convert 'this' pointer from 'const QuadPattern' to 'QuadPattern &'
Conversion loses qualifiers

Функция setCoordinate это так:

inline void setCoordinate (const std:: pair & value) {_coordinate = value; }

Почему эта ошибка?

2 ответа

Решение

Ошибка в том, что вы пытаетесь изменить объект const, возвращаемый QMutableSetIterator::value() функция.

Я считаю, что вы не можете изменить элементы своего набора таким образом, и поэтому нет такого API. Чтобы изменить все элементы, вам нужно просто очистить набор и снова вставить новые элементы.

Есть веская причина для QMutableSetIterator::value() вернуть постоянную ссылку. Элементы в наборе внутренне индексируются на основе их хеша. Как правило, вам необходимо удалить и снова вставить элемент, если вы хотите изменить его. Если вы хотите избежать копирования данных, сделайте QuadPattern неявно разделяемый класс:

class QuadPatternData : public QSharedData
{
   ...
};

class QuadPattern {
  QSharedDataPointer<QuadPatternData> d;
public:
  QuadPattern() : d(new QuadPatternData) {}
  QuadPattern(const QuadPattern & other) : d(other.d) {}
  QuadPattern(QuadPattern && other) { d.swap(other.d); }
  void setCoordinate( ... ) { d->coordinate = ...; }
  ...
};
Другие вопросы по тегам