Решаю следующую задачу: есть некоторый файл, структура которого представляет собой набор блоков. Каждый блок имеет заголовок и тело. Последний блок отмечен соответствующим идентификатором. Для обхода блоков в файле пишу собственный итератор:
/**
* @brief Single-pass input iterator.
*/
class BlockIterator : public std::iterator<std::input_iterator_tag, const DataBlock> {
private:
friend class FileReader;
FileReader* reader;
// Текущий блок, на который указывает итератор.
std::unique_ptr<DataBlock> block;
BlockIterator(FileReader* r, std::unique_ptr<DataBlock> b) noexcept : reader(r), block(std::move(b)) {
/*NOP*/
};
public:
BlockIterator& operator++() {
auto nextBlockOffset = block->offset + block->headerSize + block->bodySize;
block = reader->getBlockAt(nextBlockOffset);
// ^^^ Функция может выкидывать исключение!
return *this;
}
BlockIterator operator++(int) {
auto retval = *this;
++(*this);
return retval;
}
bool operator==(const BlockIterator& other) const {
return reader == other.reader && block == other.block;
}
bool operator!=(const BlockIterator& other) const {
return !(*this == other);
}
reference operator*() const {
return *block;
}
};
При инкременте функция getBlockAt()
может выкидывать исключение (например, если парсим невалидный файл). Как в этом случае лучше поступать: необходимо ли гарантировать отсутствие исключений при работе с итератором? Если да, то как обеспечить инвалидацию итератора и вывод ошибки?
Айфон мало держит заряд, разбираемся с проблемой вместе с AppLab
Перевод документов на английский язык: Важность и ключевые аспекты
Почему код не работает, если вместо 3 вставить число меньше 6И как это можно исправить? Код должен сортировать вектор с помощью функтора std::greater,...