Итерация по Boost Fusion:: Vector
Я пытаюсь перебрать вектор boost::fusion, используя:
typedef typename fusion::result_of::begin<T>::type t_iter;
std::cout << distance(begin(t), end(t)) << std::endl;
for(t_iter it = begin(t); it != end(t); next(it)){
std::cout<<deref(it)<<std::endl;
}
Оператор distance cout дает мне конечную длину (2), однако цикл кажется бесконечным.
Любой совет высоко ценится!
4 ответа
Вы не можете просто итерировать вектор Fusion таким образом, тип для каждого итератора может отличаться от предыдущего (и обычно это так). Я думаю, именно поэтому у вас нет it = next(it)
в вашем коде это даст ошибку компиляции.
Вы могли бы использовать boost::fusion::for_each
для этого вместе с функциональным объектом, который печатает каждый элемент в стандартный вывод:
struct print
{
template< typename T >
void operator()( T& v ) const
{
std::cout << v;
}
};
...
boost::fusion::for_each( t, print() );
fusion
Это замечательная библиотека, и теперь вы должны понимать, что она действительно отличается от того, что вы используете в повседневных программах на C++ несколькими способами, она объединяет мощь метапрограммирования во время компиляции со средой выполнения, для этого вам следует теперь, когда нет типа, который может обрабатывать все предметы в fusion
контейнер. Что это значит? это означает, что result_of::begin<T>::type
не всегда соответствует next(it)
так что вы не можете использовать fusion
итераторы в for
как это.
Очевидная проблема в вашем коде состоит в том, что вы игнорируете возвращаемое значение next
и это заставит ваш код работать вечно, но вы не можете использовать его в it = next(it)
, так как их тип может отличаться!!
Так что ты должен делать?? Вы должны использовать boost::fusion::for_each
для этой цели
next
фактически не продвигает итератор, он просто возвращает следующий.
Это можно увидеть в документах, так как функция next
принимает постоянный аргумент, что означает, что он не может изменить итератор:
template<
typename I
>
typename result_of::next<I>::type next(I const& i);
^^^^^
Проблема в том, что внутри цикла вы разыменовываете свой итератор. Когда вы подаете заявку next
на нем это ничего не значит, и поэтому ваш цикл работает вечно.