1

私はプログラムを作成し、vector.h #include、イテレータなどを使用しています...しかし、プログラムを実行すると、特定の状況下で(私はまだそれらが何であるかを理解しようとしています)、アサーションを取得しますvector.hの98行目を参照してエラーが発生しました。vector.hの98行目に移動し、次のように取得しました。

 #if _HAS_ITERATOR_DEBUGGING
        if (this->_Mycont == 0
            || _Myptr < ((_Myvec *)this->_Mycont)->_Myfirst
            || ((_Myvec *)this->_Mycont)->_Mylast <= _Myptr)
            {
            _DEBUG_ERROR("vector iterator not dereferencable");
            _SCL_SECURE_OUT_OF_RANGE;
            }

誰かがこれが何を意味するのか、そして私のプログラムの何がこの主張を引き起こしているのか教えてもらえますか?

注意:レコードの98行目は、「_ DEBUG_ERROR("vect..."」で始まる行です。

注意:これは私のプログラムのコードで、私が信じていることでエラーが発生しましたが、完全にはわかりません。

コード:

for(aI = antiviral_data.begin(); aI < antiviral_data.end();)
    {
        for(vI = viral_data.begin(); vI < viral_data.end();)
        {
            if((*aI)->x == (*vI)->x && (*aI)->y == (*vI)->y)
            {
                vI = viral_data.erase(vI);
                aI = antiviral_data.erase(aI);
            }
            else
            {
                vI++;
            }
        }
        if((*aI)->x >= maxx || (*aI)->x < 0 || (*aI)->y >= maxy || (*aI)->y < 0)
        {
            aI = antiviral_data.erase(aI);
        }
        else
        {
            aI++;
        }
    }
4

5 に答える 5

10

ランタイムは、begin()の前またはend()の後にあるイテレータを逆参照していることを検出しています。

antiviral_data7行目のベクトルの最後の項目を削除した場合を想像してみてください 。

aI = antiviral_data.erase(aI);

aIに設定されantiviral_data.end()、14行目で逆参照すると:

if((*aI)->x >= maxx ...

また、5行目:

if((*aI)->x == (*vI)->x

範囲外のイテレータを間接参照しています。

修正はaI != antiviral_data.end()、erase呼び出しの後で、ベクトルの終わりに到達していないことを確認してから、使用を続行することです。

于 2009-05-15T02:47:20.813 に答える
7

このようなことを手動で行うのではなく、STLアルゴリズムを実際に見てみたいと思いますremove_if

于 2009-05-15T03:03:01.667 に答える
5

小さな一般的なコメント:イテレータをチェックするときは、「 」ではなく「」のみend()を使用してください。したがって、コードの最初の行は次のようになります。<!=

for(aI = antiviral_data.begin(); aI != antiviral_data.end();)
{
  for(vI = viral_data.begin(); vI != viral_data.end();)
  {
    ...

ただし、Joshがすでに指摘しているように、特定のバグは7行目にあります。

于 2009-05-15T03:22:32.867 に答える
1

受け入れられた回答に加えて、slavy13の回答について詳しく説明します-
編集-そしてJoshが述べたように、この質問には直接関係ありません-参考のためにここに残しておきます)。

コード(このコードではない)は、ベクトルから要素を削除して反復を続けることができると想定する場合があります。これは誤った仮定です-ベクトルから要素を削除すると、削除された要素に続く他のすべてのイテレータは無効になります-それらが正しいと仮定することはできなくなり、それらを使い続けると「悪いこと」が発生する可能性があります。

これは、ベクトルが実際に情報を配列形式で格納するためです。要素が削除されると、後続のすべての要素が1セル下にコピーされます。イテレータはそれに応じて更新されません。

そのようなコードがSTLの特定の実装で誤って機能する可能性がありますが、他の実装では失敗する可能性があるため、そのようなことを行う場合は常にSTLドキュメントを参照することを強くお勧めします。

于 2009-05-15T04:07:24.727 に答える
-2

ベクトル内の要素を消去すると、すべてのイテレータが無効になります。

于 2009-05-15T03:37:14.907 に答える