2011-07-22 3 views
2

双方向イテレータのオペレータ<はどのように定義できますか? (リスト::イテレータ)双方向イテレータのoperator <をどのように定義できますか?

(私はリストではなく、ベクターを使用したいと思います。)

+0

なぜベクターではなくリストを使用したいのですか? –

+8

リストイテレータに 'operator <'を適用したいのはなぜですか?ユースケースは何ですか? –

+0

これは 'std :: list'かあなたのカスタム定義のリストクラスですか? – leftaroundabout

答えて

2

インポッシブル。 endまで歩く必要があります。そのためにはlist::iteratorでコード化されていないlist(起源)を知る必要があります。

(この目的のためには、listまたは起点をコンストラクタ引数として使用する関数オブジェクトを作成することができます。あるイテレータが他のイテレータより小さいかどうかを調べるには、O(n)時間がかかります。あなたは、このような比較を行うためには、リストの開始および/または終了を知る必要があるだろうので

2

あなたはこれを行うことはできません。ランダムアクセスイテレータのみがoperator<を定義します。

7

あなたはそれを直接行うことはできませんが、std::distance(x.begin(), it1)std::distance(x.begin(), it2)を計算し、それらを比較することができます。リストにはランダムアクセスがないので、リスト全体をトラバースする必要があるため、そのようなクエリの価格を支払わなければならないと予想されます。


編集:両方のイテレータがリストの終わり近くにある場合は、これはうまく機能しません。あなたは基本的にfwd1/rev1fwd2/rev2、それぞれに2つのコピーを続けるだろう、とあなたはrev*をデクリメント

[ .... <-- it1 --> .... <-- it2 --> .... ] 

:あなたはより多くの空想を取得したい場合は、両方のイテレータから外側に向かって移動し、いくつかの探検アルゴリズムを書くことができますあなたがx.begin()を打ち、x.end()に達するまでfwd*イテレータを進めるまで、イテレータを繰り返します。イテレータのペアが均等に分散されている場合、これはおそらくより良い実行時間を持つでしょう。 ++(list.end())を想定

1

は未定義の動作ではなく、list.end()に等しい、方法があります。しかし、私はこの仮説についてはわかりません。

有効な場合は、簡単なアルゴリズムを定義して、必要な結果を得ることができます。

+1

残念ながら、実際には未定義の動作です。主要な実装のうちの少なくとも1つで動作することは起こりますが、それはあなたが得られる最高の保証です。 –

関連する問題