2

TriangleMesh、PointClouds、Edgesets など、頂点に基づいて幾何学的オブジェクトを実装するクラスがたくさんあります。それらはすべて VertexBasedGeometry から継承します。私は今、それらすべてがその頂点の参照で双方向イテレータを返すようにしたいと考えています。これにより、テンプレート化されていない方法で任意の VertexBasedGeometry の頂点にアクセスできます。さて、私はイテレータにあまり慣れていないので、これはかなり難しいことがわかりました。私の試みは次のようになります:

class VertexBasedGeometry : public Geometry
{
public:

typedef std::iterator<std::bidirectional_iterator_tag,defines::Vector3 >  VertexIterator;

VertexBasedGeometry(){};

virtual VertexIterator begin()=0;
virtual VertexIterator end()=0;
};

VertexBasedGeometry から継承する TraingleMesh では、頂点を含む std::vector の begin イテレータを返すことで関数 begin を実装しようとしています。これにより、gcc 4.2 (apple) で次のコンパイラ エラーが発生します。

Mesh.cpp:25: error: conversion from '__gnu_cxx::__normal_iterator<defines::Vector<double, 3>*, std::vector<defines::Vector<double, 3>, std::allocator<defines::Vector<double, 3> > > >' to non-scalar type 'std::iterator<std::bidirectional_iterator_tag, defines::Vector<double, 3>, long int, defines::Vector<double, 3>*, defines::Vector<double, 3>&>' requested

私の質問は次のとおりです。なぜこれが機能しないのですか。これを機能させるにはどうすればよいですか? イテレータについて詳しく読んでいると、双方向イテレータの共通の型を見つけることができないと少し感じました。そうですか? 一部のクラスでは、頂点が std::vector 以外のコンテナーに格納されている場合があります。他のクラスでは、共通の型に適応させたい (stl に準拠していない) イテレーターが既に提供されています。これを実装する方法についての推奨事項をお待ちしています。

4

3 に答える 3

2

std::iterator は派生元のタグ クラスにすぎず、イテレータの型はコンパイル時に実装クラスに認識されている必要があります。イテレータの実装を反復コードから隠したい場合は、Thomas Becker の any_iteratorなどの間接レベルを追加する必要があります。

于 2011-10-06T11:47:40.520 に答える
1

イテレータは単なる緩い概念であり、実際のイテレータクラスはいかなる意味でも関連していません。一般に、クラスの完全なイテレータクラスを作成することはできません。

イテレータは特定の共通点を共有しているため、でプローブできるようにイテレータを設計する必要がありますstd::iterator_traits。これは、特定のイテレータ実装に多くの類似したコードが含まれることを意味します(Boostのイテレータファサードのようなものが役立つ場合があります)。それでも、クラスのインターフェイス(、、begin()などend()find()は、独自のイテレータタイプを返す必要があり、イテレータの実装(つまり、インクリメント演算子と逆参照演算子)を記述する必要があります

于 2011-10-06T12:31:49.097 に答える
0

BidirectionalIteratorはクラスではなく、概念です。概念は、指定されたセマンティクスを持つ一連の要件と式で構成されます。クラスが概念のすべての要件を満たす場合、それはこの概念のモデルであると言われます。つまり、標準ライブラリはサブタイプのポリモーフィズムではなく概念に基づいて機能するため、一部の概念の反復子に共通のクラスはありません。

だから何std::iteratorですか?特定のイテレータの特性の定義を容易にするヘルパーですが、機能は提供しません。コンパイル時のメタプログラミングのみを有効にします。

Boost.Iteratorsのような特定の反復子をモデル化する独自のクラスを実装するのに役立つツールがいくつかあります。

于 2011-10-06T12:41:11.763 に答える