C ++ 17 представил концепцию ContiguousIterator http://en.cppreference.com/w/cpp/iterator.
Однако не похоже, что есть планы contiguous_iterator_tag
(так же, как мы сейчас имеем random_access_iterator_tag
) сообщает std::iterator_traits<It>::iterator_category
,
Почему contiguous_iterator_tag
отсутствует?
Существует ли обычный протокол, чтобы определить, является ли итератор смежным?
Или тест времени компиляции?
В прошлом я упоминал, что для контейнеров если есть .data()
член, который преобразуется в указатель на ::value
типа и есть .size()
член, конвертируемый в разность указателей, тогда следует предположить, что контейнер является смежным, но я не могу использовать аналогичную функцию итераторов.
Одним из решений может быть также иметь data
функция для смежных итераторов.
Конечно, смежная концепция работает, если &(it[n]) == (&(*it)) + n
, для всех n
, но это не может быть проверено во время компиляции.
РЕДАКТИРОВАТЬЯ нашел это видео, которое помещает это в более широкий контекст концепций C ++. CppCon 2016: «Построение и расширение иерархии итераторов в современном многоядерном мире» Патрик Недзельски. Решение использует концепции (Lite), но в конце идея состоит в том, что смежные итераторы должны реализовать pointer_from
функция (так же, как мой data(...)
функция).
Вывод состоит в том, что концепции помогут формализовать теорию, но они не магические, в том смысле, что кто-то где-то определит новые, особенно именованные функции, через смежные итераторы.
Доклад обобщается на сегментированные итераторы (с соответствующими функциями segment
а также local
), к сожалению, ничего не говорится о пошаговых указателях.
Обоснование дано в N4284, которая является принятой версией непрерывного предложения итераторов:
В этой статье термин «непрерывный итератор» вводится как уточнение итератора с произвольным доступом без введения соответствующего
contiguous_iterator_tag
Обнаружено, что он нарушает код во время обсуждений в Issaquah статьи Невина Либера N3884 «Непрерывные итераторы: уточнение итераторов произвольного доступа».
Некоторый код был взломан, потому что предполагалось std::random_access_iterator
не мог быть уточнен, и имел явные проверки против этого. По сути, он сломал плохой код, который не полагался на полиморфизм для проверки категорий итераторов, но тем не менее он сломал код, поэтому contiguous_iterator_tag
был удален из предложения.
Также возникла дополнительная проблема с std::reverse_iterator
-подобные классы: обратный непрерывный итератор не может быть непрерывным итератором, но обычным итератором с произвольным доступом. Эта проблема могла быть решена за std::reverse_iterator
, но больше пользовательских оболочек итераторов, которые дополняют итератор при копировании его категории итераторов, либо лгали, либо перестали корректно работать (например, повышающие адаптеры итераторов).
Кстати, есть планы вернуть эквивалент std::contiguous_iterator_tag
с несколькими обходными путями, чтобы заставить его работать с интеграцией Ranges TS в C ++ 20.
Других решений пока нет …