Доступ ко всем членам коллекции

Для доступа к своим элементам классы коллекций массивов MFC (как шаблонные, так и нешаблонные) используют индексы. Для описания в заданной позиции в коллекции классы коллекций списков и схем MFC (как шаблонные, так и нешаблонные) используют индикатор типа POSITION . Чтобы получить доступ к одному или нескольким членам этих коллекций, сначала следует инициализировать индикатор позиции, а затем повторно передавать эту позицию в коллекцию с запросом на возврат следующего элемента. Коллекция не отвечает за поддержание сведений о состоянии хода выполнения итерации. Эта информация хранится в индикаторе позиции. Однако, принимая во внимание конкретную позицию, коллекция отвечает за возврат следующего элемента.

В приведенных далее процедурах показана итерация в трех основных типах коллекций в MFC.

Итерация массива

  1. Используйте последовательные номера индекса с функцией-членом 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 . Для классов коллекций типизированных указателей (массивов или списков) первый параметр указывает базовый класс, второй параметр указывает тип для хранения.

    Класс CTypedPtrArray также перегружает оператор [ ] , чтобы можно было использовать обычный синтаксис массива для доступа к элементам массива. Альтернативой инструкции в теле приведенного выше цикла for является

    CPerson *thePerson = myArray[i];
    

    Этот оператор существует как в, так const и в версиях, отличныхconst от версии. Версия const , которая вызывается для const массивов, может отображаться только в правой части инструкции назначения.

Итерация списка

  1. Для прохода по списку используйте функции-члены GetHeadPosition и GetNext :

    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 .

Итерация схемы

  1. Используйте 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.

    Примечание.

    При работе с нешаблонными схемами компилятору требуется ссылка на указатель CObject в последнем параметре на GetNextAssoc. При воде данных необходимо привести указатели к этому типу, как показано в следующем примере.

    Шаблонное решение проще в использовании и помогает обеспечить более высокий уровень безопасности типов. Как видно из примера ниже, нешаблонный код более сложен.

    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.

См. также

Коллекции