Partilhar via


Como fazer uma coleção Type-Safe

Este artigo explica como fazer coleções de tipos seguras para os seus próprios tipos de dados. Os tópicos incluem:

A Microsoft Foundation Class Library fornece coleções seguras para tipos predefinidas com base em modelos C++. Como são modelos, essas classes ajudam a fornecer segurança de tipo e facilidade de uso sem a conversão de tipo e outros trabalhos extras envolvidos no uso de uma classe não modelo para essa finalidade. O exemplo MFC COLLECT demonstra o uso de classes de coleção baseadas em modelo em um aplicativo MFC. Em geral, use essas classes sempre que escrever um novo código de coleções.

Usando classes Template-Based para segurança de tipo

Para usar classes baseadas em modelo

  1. Declare uma variável do tipo de classe de coleção. Por exemplo:

    CList<int, int> m_intList;
    
  2. Invoque as funções membro do objeto da coleção. Por exemplo:

    m_intList.AddTail(100);
    m_intList.RemoveAll();
    
  3. Se necessário, implemente as funções auxiliares e SerializeElements. Para obter informações sobre como implementar essas funções, consulte Implementando funções auxiliares.

Este exemplo mostra a declaração de uma lista de inteiros. O primeiro parâmetro na etapa 1 é o tipo de dados armazenados como elementos da lista. O segundo parâmetro especifica como os dados devem ser passados e retornados de funções de membro da classe de coleção, como Add e GetAt.

Implementando funções auxiliares

As classes CArrayde coleção baseadas em modelo , CListe CMap usam cinco funções auxiliares globais que você pode personalizar conforme necessário para sua classe de coleção derivada. Para obter informações sobre essas funções auxiliares, consulte Auxiliares de classe de coleção na Referência MFC. A implementação da função de serialização é necessária para a maioria dos usos das classes de coleção baseadas em modelo.

Elementos de serialização

As CArray, CList e CMap classes chamam SerializeElements para armazenar elementos de coleção ou lê-los de um arquivo.

A implementação padrão da SerializeElements função auxiliar faz uma gravação bit a bit dos objetos para o arquivo, ou uma leitura bit a bit do arquivo para os objetos, dependendo se os objetos estão sendo armazenados ou recuperados do arquivo. Substituir SerializeElements se esta ação não for apropriada.

Se sua coleção armazena objetos derivados de CObject e você usa a IMPLEMENT_SERIAL macro na implementação da classe de elemento de coleção, você pode aproveitar a funcionalidade de serialização embutida em CArchive e CObject:

CArray< CPerson, CPerson& > personArray;

template <> void AFXAPI SerializeElements <CPerson>(CArchive& ar,
   CPerson* pNewPersons, INT_PTR nCount)
{
   for (int i = 0; i < nCount; i++, pNewPersons++)
   {
      // Serialize each CPerson object
      pNewPersons->Serialize(ar);
   }
}

Os operadores de inserção sobrecarregados para CArchive chamam CObject::Serialize (ou uma substituição dessa função) para cada objeto CPerson.

Usando classes de coleção sem modelo

MFC também suporta as classes de coleção introduzidas com MFC versão 1.0. Essas classes não são baseadas em modelos. Eles podem ser usados para conter dados dos tipos CObject*suportados , UINT, DWORD, e CString. Você pode usar essas coleções predefinidas (como CObList) para armazenar coleções de quaisquer objetos derivados do CObject. MFC também fornece outras coleções predefinidas para manter tipos primitivos, como UINT ponteiros vazios (void*). Em geral, no entanto, muitas vezes é útil definir suas próprias coleções seguras para armazenar objetos de uma classe mais específica e seus derivados. Observe que fazer isso com as classes de coleção não baseadas em modelos é mais trabalhoso do que usar as classes baseadas em modelos.

Há duas maneiras de criar coleções com segurança de tipo com as coleções sem modelo:

  1. Use as coleções que não são de modelo, com conversão de tipos, se necessário. Esta é a abordagem mais fácil.

  2. Derive e estenda uma coleção segura para tipos não baseada em modelo.

Para usar coleções sem modelo com conversão de tipo

  1. Use uma das classes não modelo, como CWordArray, diretamente.

    Por exemplo, você pode criar um CWordArray e adicionar quaisquer valores de 32 bits a ele e, em seguida, recuperá-los. Não há mais nada a fazer. Basta usar a funcionalidade predefinida.

    Você também pode usar uma coleção predefinida, como CObList, para armazenar quaisquer objetos derivados de CObject. Uma CObList coleção é definida para manter ponteiros para CObject. Quando você recupera um objeto da lista, talvez seja necessário converter o resultado para o tipo adequado, já que as CObList funções retornam ponteiros para CObject. Por exemplo, se armazenar objetos CPerson numa coleção CObList, terá de converter um elemento recuperado num ponteiro para um objeto CPerson. O exemplo a seguir usa uma CObList coleção para armazenar CPerson objetos:

    CPerson* p1 = new CPerson();
    CObList myList;
    
    myList.AddHead(p1);   // No cast needed
    CPerson* p2 = (CPerson*)myList.GetHead();
    

    Esta técnica de usar um tipo de coleção predefinido e fundição conforme necessário pode ser adequada para muitas das suas necessidades de coleção. Se você precisar de mais funcionalidade ou mais segurança de tipo, use uma classe baseada em modelo ou siga o próximo procedimento.

Para derivar e estender uma coleção segura para tipos sem modelo

  1. Derive sua própria classe de coleção de uma das classes não modelo predefinidas.

    Ao derivar sua classe, você pode adicionar funções de wrapper de tipo seguro para fornecer uma interface de tipo seguro para funções existentes.

    Por exemplo, se derivou uma lista de CObList para manter objetos CPerson, poderá adicionar as funções AddHeadPerson e GetHeadPerson de wrapper, conforme mostrado abaixo.

    class CPersonList : public CObList
    {
    public:
       void AddHeadPerson(CPerson* person)
       {
          AddHead(person);
       }
    
       const CPerson* GetHeadPerson()
       {
          return (CPerson*)GetHead();
       }
    };
    

    Essas funções de wrapper fornecem uma maneira segura de tipo para adicionar e recuperar CPerson objetos da lista derivada. Você pode ver que, para a função GetHeadPerson, você está simplesmente a encapsular o casting de tipo.

    Você também pode adicionar novas funcionalidades definindo novas funções que ampliam as capacidades da coleção, ao invés de apenas encapsular a funcionalidade existente em wrappers de tipos seguros. Por exemplo, o artigo Excluindo todos os objetos em uma coleção CObject descreve uma função para excluir todos os objetos contidos em uma lista. Esta função pode ser adicionada à classe derivada como uma função de membro.

Ver também

Coleções