Iteradores
Parte da seção Programação Orientada a Objetos do Journey de C++ da Coddy. Lição 72 de 104.
Iteradores são objetos que atuam como uma ponte entre contêineres e algoritmos. Eles fornecem uma maneira uniforme de acessar elementos em qualquer contêiner, independentemente de como esse contêiner armazena seus data internamente. Pense em um iterador como um ponteiro generalizado que sabe como percorrer um contêiner.
Todo contêiner da STL fornece os métodos begin() e end(). O iterador begin() aponta para o primeiro elemento, enquanto end() aponta para uma posição após o último elemento — um sentinela que marca onde parar:
#include <vector>
#include <iostream>
int main() {
std::vector<int> nums = {10, 20, 30};
for (std::vector<int>::iterator it = nums.begin(); it != nums.end(); ++it) {
std::cout << *it << " "; // Desreferenciar para obter o valor
}
// Saída: 10 20 30
}A palavra-chave auto simplifica significativamente as declarações de iteradores:
for (auto it = nums.begin(); it != nums.end(); ++it) {
*it *= 2; // Modificar elementos através do iterador
}
// nums agora é {20, 40, 60}Os iteradores vêm em diferentes categorias com base em suas capacidades. Iteradores de acesso aleatório (como os de vector) oferecem suporte a operações aritméticas, como it + 3 ou it1 - it2.
Iteradores bidirecionais (de list, map) podem avançar e retroceder com ++ e --. Iteradores de avanço podem se mover apenas em uma direção.
Para a travessia reversa, use rbegin() e rend():
for (auto rit = nums.rbegin(); rit != nums.rend(); ++rit) {
std::cout << *rit << " "; // Imprime em ordem inversa
}Desafio
FácilVamos criar um sistema de controle de inventário que usa iteradores para percorrer e manipular coleções de itens. Você praticará o uso de diferentes tipos de iteradores para navegar pelos dados de várias maneiras.
Você organizará seu código em dois arquivos:
Inventory.h: defina uma classeInventoryque gerencie uma coleção de quantidades de itens armazenadas em umstd::vector<int>.Sua classe deve fornecer estes métodos:
addItem(int quantity): adiciona uma quantidade de item ao inventárioprintForward(): usa iteradores combegin()eend()para imprimir todas as quantidades separadas por espaços, seguidas por uma nova linhaprintReverse(): usa iteradores reversos comrbegin()erend()para imprimir todas as quantidades na ordem inversa, separadas por espaços, seguidas por uma nova linhadoubleAll(): usa iteradores para percorrer o vetor e dobrar cada quantidade no próprio localgetTotal(): usa iteradores para calcular e retornar a soma de todas as quantidades
Use a palavra-chave
autonas declarações dos iteradores para manter o código limpo.main.cpp: leia quatro entradas inteiras (cada uma em uma linha separada) que representem as quantidades dos itens.Crie um
Inventorye adicione as quatro quantidades. Em seguida, demonstre o uso de iteradores:- Imprima
Forward:seguido da chamada deprintForward() - Imprima
Reverse:seguido da chamada deprintReverse() - Imprima
Total: <sum>usandogetTotal() - Chame
doubleAll()para modificar as quantidades - Imprima
After doubling:seguido da chamada deprintForward() - Imprima
New total: <sum>usandogetTotal()
- Imprima
Por exemplo, com as entradas 10, 25, 15 e 30:
Forward: 10 25 15 30
Reverse: 30 15 25 10
Total: 80
After doubling: 20 50 30 60
New total: 160Este desafio permite que você pratique tanto a leitura de elementos por meio de iteradores (para imprimir e somar) quanto a modificação de elementos por meio de iteradores (para dobrar). Você também verá como os iteradores reversos tornam a travessia para trás simples, sem qualquer manipulação de índices.
Experimente você mesmo
#include <iostream>
#include "Inventory.h"
using namespace std;
int main() {
// Ler quatro entradas inteiras
int q1, q2, q3, q4;
cin >> q1;
cin >> q2;
cin >> q3;
cin >> q4;
// TODO: Criar um objeto Inventory
// TODO: Adicionar todas as quatro quantidades ao inventário
// TODO: Imprimir "Forward: " e então chamar printForward()
// TODO: Imprimir "Reverse: " e então chamar printReverse()
// TODO: Imprimir "Total: " seguido do resultado de getTotal()
// TODO: Chamar doubleAll() para modificar as quantidades
// TODO: Print "After doubling: " then call printForward()
// TODO: Imprimir "New total: " seguido do resultado de getTotal()
return 0;
}
Esta lição inclui um quiz rápido. Comece a lição para respondê-lo e acompanhar seu progresso.
Todas as lições de Programação Orientada a Objetos
1Fundamentos de POO
Arquivos externosBuild e compilação em C++Arquivos de cabeçalho e arquivos-fonteNamespaces e escopoIntrodução à POO em C++Classes vs. objetosO ponteiro 'this'Métodos (funções membro)Atributos (membros de dados)Noções básicas de construtores e destruidoresRevisão - calculadora simples4Propriedades de Classe
Membros de Instância vs. EstáticosGetters e SettersFunções Membro ConstPalavra-chave MutableMétodos e Variáveis EstáticosFunções e Classes FriendRevisão - Gerenciador de Contas Bancárias7Herança
Herança básicaNíveis de acesso da herançaOrdem de chamada de construtor e destrutorSobrescrita de métodosFunções virtuais e VTableHerança múltiplaHerança virtualRevisão - Hierarquia de funcionários10Visão geral da STL
Visão geral e filosofia da STLContêineres da STLIteradoresAlgoritmos da STLFunctors e expressões lambdaRecapitulação - Frequência de palavras13Padrões de Projeto — Parte 1
Introdução aos Padrões de ProjetoPadrão SingletonFactory e Abstract FactoryPadrão BuilderPadrão ObserverPadrão Strategy2Gerenciamento de Memória
Memória Stack vs. HeapPonteiros e ReferênciasMemória Dinâmica (new/delete)Ponteiros Inteligentes em C++RAII em C++Revisão - Gerenciador de Array Dinâmico5Encapsulamento
Especificadores de acesso em C++Especificadores de acesso em profundidadeOcultação de informaçõesStruct vs ClasseClasses aninhadas e internasRecapitulação - Sistema de registros de alunos8Polimorfismo
Polimorfismo em compilação vs. execuçãoSobrecarga de funçõesFunções virtuais revisadasFunções virtuais purasClasses abstratasDesign de interfaces em C++Conversão dinâmica e RTTIRecapitulação — Calculadora de formas11Conceitos Avançados de OOP
Composição vs. HerançaMixins via CRTPIdioma PimplApagamento de TiposClasses Enum e Tipagem ForteTratamento de Exceções em OOPHierarquias de Exceções Personalizadas14Padrões de Projeto — Parte 2
Padrão CommandPadrão AdapterPadrão DecoratorPadrão Template MethodPadrão StatePadrão CompositeRAII como Padrão3Construtores e Destrutores
Construtor PadrãoConstrutor ParametrizadoConstrutor de CópiaConstrutor de MovimentoListas de Inicialização do ConstrutorConstrutores DelegantesAprofundamento em DestrutoresRegra dos Três / Cinco / ZeroRevisão - Classe String6Sobrecarga de Operadores
Introdução à Sobrecarga de OperadoresSobrecarga de Operadores AritméticosSobrecarga de Operadores de ComparaçãoOperadores de FluxoSobrecarga do Operador de AtribuiçãoSobrecarga dos Operadores [] e ()Operadores de Conversão de TipoRecapitulação - Classe Matrix9Templates
Templates de FunçõesTemplates de ClassesEspecialização de TemplatesTemplates VariádicosNoções Básicas de SFINAE e Traits de TiposRecapitulação - Contêiner GenéricoPratique por conta própria: Compilador de C++ online