将 end() 迭代器转换为指针
Convert the end() iterator to a pointer
说到重点:以下内容安全吗?
vector<int> v;
int const* last = &*v.end();
// last is never dereferenced
我担心的是,从迭代器获取普通旧指针的技巧会强制取消引用 end() 迭代器,这是无效的......哪怕只是为了把指针拿回来!
Backgroud:我正在尝试创建一个由任意类型(尤其是整数和指向对象的指针)索引的条目集合。
template<class IT>
/// requires IT implements addition (e.g. int, random-access iterator)
class IndexingFamily {
public:
using IndexType = IT;
IndexingFamily(IndexType first, IndexType last);
int size() const;
IndexType operator[](int i) const;
private:
IndexType first;
IndexType last;
};
template<class IT> IndexingFamily<IT>::
IndexingFamily(IndexType first, IndexType last)
: first(first)
, last(last) {}
template<class IT> auto IndexingFamily<IT>::
size() const -> int {
return last-first;
}
template<class IT> auto IndexingFamily<IT>::
operator[](int i) const -> IndexType {
return first+i;
}
template<class IT, class ET>
struct IndexedEntry {
using IndexType = IT;
using EntryType = ET;
IndexType index;
EntryType entry;
};
template<class IT, class ET>
class CollectionOfEntries {
public:
using IndexType = IT;
using EntryType = ET;
/// useful methods
private:
IndexingFamilyType indexingFamily;
vector<EntryType> entries;
};
struct MyArbitraryType {};
int main() {
MyArbitraryType obj0, obj1, obj2;
vector<MyArbitraryType> v = {obj0,obj1,obj2};
using IndexType = MyArbitraryType const*;
IndexingFamily<IndexType> indexingFamily(&*v.begin(),&*v.end());
using EntryType = double;
using IndexedEntryType = IndexedEntry<IndexType,EntryType>;
IndexedEntry entry0 = {&obj0,42.};
IndexedEntry entry1 = {&obj1,43.};
vector<IndexedEntryType> entries = {entry0,entry1};
CollectionOfEntries coll = {indexingFamily,entries};
return 0;
}
取消引用end()
迭代器会给出任何标准容器的未定义行为。
对于向量,您可以使用以下命令获取与end()
迭代器对应的指针
pointer_to_end = v.empty() ? 0 : (&(*v.begin()) + v.size());
或
pointer_to_end = v.data() + v.size(); // v.data() gives null is size is zero
需要检查v.empty()
,因为如果v
为空,则v.begin() == v.end()
. 对于 C++11 或更高版本,通常认为最好使用上述nullptr
而不是0
。
成员函数返回的迭代器在向量的最后一个元素之后end()
"点"。您不得取消引用它。否则,程序将具有未定义的行为。
您可以通过以下方式获取相应的指针
vector<int> v;
int const *last = v.data() + v.size();
如果你想使用成员函数end()返回的迭代器,你可以写
vector<int> v;
int const *last = v.data() + std::distance( v.begin(), v.end() );
考虑到成员函数 data() 返回 vector 数据占用的内存范围的原始指针。
相关文章:
- 转换指针引用的字符串
- 无法向上转换指针到指针参数
- 混合转换指针和引用
- 堆栈对象的强制转换指针
- 基类到派生模板类的强制转换指针,而不知道类型
- 删除类型转换指针的最佳方法
- 管理到本机值类转换:强制转换指针是否安全?
- 转换指针类型
- 为什么函数不能正确强制转换指针(从基类到派生类)
- 当我们递增下面的类型转换指针时会发生什么?
- 类型强制转换指针构造函数调用
- 如何转换(指针向量)-->(指向指针数组的指针)
- 如何从类功能转换指针
- 在C++对象中:我应该使用父类强制转换指针,还是应该使用实际类本身进行强制转换
- Delphi中的类型转换指针添加
- C++分段错误(核心转储)错误 - 强制转换指针/将函数值返回到线程
- 以C++和运算符优先级键入指向数组成员的强制转换指针
- C++动态强制转换指针的内存清理
- 转换指针和引用的好处
- 在c++中转换指针