[英]Determine if a (c++) iterator is reverse
我想要一种在编译时确定迭代器是否反向的机制。
迭代器特征只能帮助解决迭代器类型的类别 ,而我需要的是以下内容:
template<typename IterType>
struct IsReverseIterator
{
enum { Yes = /* Implementation of the mechanism */ };
}
我有一个解决方案,尽管它有一个小的缺点,但是还必须提供容器类型:
typedef char TrueT;
typedef struct { TrueT _[2]; } FalseT;
template<typename Cont> TrueT IsReverseIterator(typename Cont::const_reverse_iterator);
template<typename Cont> FalseT IsReverseIterator(...);
它显然使用了SFINAE,可以这样使用:
std::vector<int> v;
std::cout << (sizeof(IsReverseIterator<std::vector<int>>(v.begin())) == sizeof(TrueT)) << std::endl;
std::cout << (sizeof(IsReverseIterator<std::vector<int>>(v.rbegin())) == sizeof(TrueT)) << std::endl;
有任何想法吗?
编辑
为了说明我要搜索的内容,例如以下代码
template<typename Cont, typename It>
bool points_to_last_element(Cont const &container, It iter)
{
return iter == container.rend();
// here I would like to dispatch to 2 implementations
// one for reverse iterators and one for forward where this would happen
// return iter == container.end();
}
这是一个虚拟的示例,请不要被我已经处理过的代码或者我可能会有两个重载,一个带有Cont::reverse_iterator
而另一个带有Cont::iterator
的事实所Cont::reverse_iterator
。 我不会/无法更改该设计,我只是在尝试一种更优雅的方法(如果有)在内部进行处理。 我再次重申那是一个虚拟的例子。
#include <iterator>
#include <type_traits>
template<typename Iter>
struct is_reverse_iterator : std::false_type { };
template<typename Iter>
struct is_reverse_iterator<std::reverse_iterator<Iter>>
: std::integral_constant<bool, !is_reverse_iterator<Iter>::value>
{ };
您还可以为所有作为反向迭代器的用户定义迭代器特化特征。
一种简单的方法。 它易于使用,可以确定某项是否为反向迭代器,并且可以根据需要在const反向迭代器之间进行区分。
#include <iostream>
template<typename Container, typename T>
using IsRegRevIter = std::is_same<T,typename Container::reverse_iterator>;
template<typename Container, typename T>
using IsConstRevIter = std::is_same<T,typename Container::const_reverse_iterator>;
template<typename Container, typename T>
struct IsRevIter
{
const static bool value = IsRegRevIter<Container,T>::value
|| IsConstRevIter<Container,T>::value;
};
int main()
{
using Container = std::list<int>;
Container myList = {1,2,3,4,5,6};
auto RI = myList.rbegin();
auto I = myList.begin();
std::cout << std::endl << std::boolalpha << IsRevIter<Container,decltype(RI)>::value; //true
std::cout << std::endl << std::boolalpha << IsRegRevIter<Container,decltype(RI)>::value; //true
std::cout << std::endl << std::boolalpha << IsConstRevIter<Container,decltype(RI)>::value; //false (it is not const).
std::cout << std::endl << std::boolalpha << IsRevIter<Container,decltype(I)>::value; //false
return 0;
}
输出:
假
真正
假
假
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.