次の方法で共有


コレクションの全メンバーへのアクセス

MFC の配列コレクション クラスでは、テンプレート クラスでも非テンプレート クラスでも、インデックスを使って要素にアクセスします。 MFC のリスト コレクション クラスおよびマップ コレクション クラスでは、テンプレート クラスでも非テンプレート クラスでも、POSITION 型のインジケーターを使ってコレクション内の位置を指定します。 これらのコレクションの 1 つ以上のメンバーにアクセスするには、まず、ポジション インジケーターを初期化し、次にそのポジションを繰り返しコレクションに引き渡して、次の要素の位置を問い合わせます。 コレクションは、繰り返しの進行についての状態情報を保持していません。 この情報は、ポジション インジケーターで保持します。 一方、コレクションは、指定されたポジションの次の要素を返します。

次に、MFC が提供する代表的な 3 種類のコレクションに対する繰り返し処理について説明します。

  • 配列に繰り返しアクセスするには

  • リストに繰り返しアクセスするには

  • マップに繰り返しアクセスするには

配列に繰り返しアクセスするには

  • 連続したインデックス番号を指定して、GetAt メンバー関数を呼び出します。

    CTypedPtrArray<CObArray, CPerson*> myArray;
    
    myArray.Add(new CPerson());
    for (int i = 0; i < myArray.GetSize();i++)
    {
       CPerson* thePerson = myArray.GetAt(i);
       thePerson->AssertValid();
    }       
    

    この例では、CPerson オブジェクトへのポインターを格納する型付きポインター配列を使っています。 この配列の基本クラスは、定義済みの非テンプレート クラスである CObArray クラスです。 GetAt は、CPerson オブジェクトへのポインターを返します。 型付きポインター コレクション クラスの場合は、配列でもリストでも、最初のパラメーターで基本クラスを指定し、2 番目のパラメーターで格納するデータの型を指定します。

    CTypedPtrArray クラスでは、さらに [ ] 演算子をオーバーロードして、配列の要素を従来の添字付け構文でもアクセスできます。 上の for ループ本体の文は、次のように書き換えることができます。

    CPerson* thePerson = myArray[i];
    

    この演算子は const 版と非 const 版があります。 const 版は、const の配列に使われ、代入文の右辺に書くことができます。

リストに繰り返しアクセスするには

  • リスト内の項目を順に処理するには、GetHeadPositionGetNext の 2 つのメンバー関数を使用します。

    CTypedPtrList<CObList, CPerson*> myList;
    
    myList.AddHead(new CPerson());
    POSITION pos = myList.GetHeadPosition();
    while(pos != NULL)
    {
       CPerson* thePerson = myList.GetNext(pos);
       thePerson->AssertValid();
    }
    

    この例では、型付きポインター配列に CPerson オブジェクトへのポインターを格納します。 リストの宣言は、「配列に繰り返しアクセスするには」の配列宣言に似ていますが、基本クラスとして CObList クラスを使用します。 GetNext は CPerson オブジェクトへのポインターを返します。

マップに繰り返しアクセスするには

  • GetStartPosition でマップの先頭位置を取得し、GetNextAssoc でマップから次のキーと値を順次取得します。次に例を示します。

    CMap<CString, LPCTSTR, CPerson*, CPerson*> myMap;
    CPerson myPerson;
    
    myMap.SetAt(_T("Bill"), &myPerson);
    POSITION pos = myMap.GetStartPosition();
    while(pos != NULL)
    {
       CPerson* pPerson;
       CString string;
       // Get key (string) and value (pPerson)
       myMap.GetNextAssoc(pos, string, pPerson);
       // Use string and pPerson
    }       
    

    この例では、型付きポインター コレクションではなく、簡単なマップ テンプレートを使用しています。このテンプレートは、CString 型のキーを使用し、CPerson オブジェクトへのポインターを格納します。 GetNextAssoc などのアクセス関数を使用すると、CPerson オブジェクトへのポインターが返されます。 代わりに非テンプレート マップ コレクションを使用すると、CObject へのポインターが返されるので、CPerson へのポインターに型キャストする必要があります。

    注意

    非テンプレート マップの場合、コンパイラは GetNextAssoc の最後のパラメーターとして CObject ポインターへの参照を必要とします。 したがって、入力時にポインターを CObject 型にキャストする必要があります。次に例を示します。

    テンプレートを使用すると、コードがより単純になり、タイプ セーフもさらに確実になります。 テンプレートを使用しないコードは、次のように複雑です。

    CMapStringToOb myMap;    // A nontemplate collection class
    CPerson myPerson;
    myMap.SetAt(_T("Bill"), &myPerson);
    
    POSITION pos = myMap.GetStartPosition();
    while(pos != NULL)
    {
       CPerson* pPerson;
       CString string;
       // Gets key (string) and value (pPerson)
       myMap.GetNextAssoc(pos, string, 
                         (CObject*&)pPerson);
       ASSERT(pPerson->IsKindOf(
                 RUNTIME_CLASS(CPerson)));
       // Use string and pPerson
    }
    

詳細については、「CObject コレクションの全オブジェクトの削除」を参照してください。

参照

概念

コレクション クラス