Recapitulação - Sistema de registros de alunos
Parte da seção Programação Orientada a Objetos do Journey de C++ da Coddy. Lição 39 de 104.
Hora de colocar em prática seus conhecimentos sobre encapsulamento! Neste desafio, você criará um Sistema de Registros de Alunos que demonstra o uso adequado de especificadores de acesso, ocultação de informações e classes aninhadas.
Seu sistema gerenciará os dados dos alunos com estes princípios de encapsulamento:
- Membros de dados privados para proteger informações confidenciais, como notas e IDs dos alunos
- Interface pública com getters e setters controlados
- Uma classe aninhada para representar as notas de cursos individuais, mantendo esse detalhe de implementação contido na classe do aluno
Esta é a estrutura que você implementará:
class Student {
public:
class Grade { // Classe aninhada para notas do curso
// ...
};
// Interface pública para interagir com os dados do estudante
private:
std::string name;
int studentId;
// Coleção de notas
};Este desafio combina tudo deste capítulo: escolher níveis de acesso apropriados, ocultar detalhes de implementação por trás de uma interface limpa e usar classes aninhadas para organizar tipos relacionados. Pense com cuidado sobre o que deve ser acessível e o que deve permanecer oculto.
Desafio
FácilVamos criar um Sistema de Registros de Alunos que reúne tudo o que você aprendeu sobre encapsulamento. Você criará um sistema no qual os dados dos alunos são devidamente protegidos, as notas são gerenciadas por meio de uma classe aninhada e todas as interações acontecem por meio de uma interface pública simples.
Você criará dois arquivos para organizar seu código:
Student.h: Defina uma classeStudentque demonstre o encapsulamento adequado com uma classeGradeaninhada.Sua classe
Gradeaninhada (declarada na seção pública deStudent) deve armazenar o nome de uma disciplina (string) e uma nota (double). Forneça um construtor que receba ambos os valores e disponibilize os métodosgetCourseName()egetScore()para acessar os dados. A classeGrademantém seus dados privados; mesmo estando aninhada dentro deStudent, ela ainda mantém seu próprio encapsulamento.A classe
Studentdeve ter membros privados para o nome do aluno (string), o ID do aluno (int) e uma coleção de ponteiros paraGrade. Forneça:- Um construtor que receba o nome e o ID do aluno
- Os getters
getName()egetStudentId()(ambos const) - Um método
addGrade(const std::string& course, double score)que crie uma novaGradee a adicione ao registro do aluno (adicione somente se a nota estiver entre 0 e 100, inclusive) - Um método
getAverageGrade()(const) que calcule e retorne a média de todas as notas, ou 0.0 se não houver notas - Um método
displayRecord()(const) que exiba o registro completo do aluno
Não se esqueça de liberar as notas alocadas dinamicamente no destrutor e incluir guardas de cabeçalho adequadas.
main.cpp: Leia o nome do aluno, o ID do aluno e as notas de três disciplinas a partir da entrada. O formato da entrada será de cinco linhas: nome, ID e, em seguida, três linhas, cada uma contendo o nome de uma disciplina e a nota separados por um espaço (por exemplo,Math 95.5).Crie um
Studentcom o nome e o ID, adicione as três notas e, em seguida, exiba o registro completo.O formato de saída de
displayRecord()deve ser:Student: <name> (ID: <id>) Grades: <course1>: <score1> <course2>: <score2> <course3>: <score3> Average: <average>
Formate todas as notas e a média com uma casa decimal usando std::fixed e std::setprecision(1) de <iomanip>. Converta o ID usando std::stoi() e as notas usando std::stod().
Este desafio combina membros de dados privados, getters públicos, setters controlados com validação e uma classe aninhada: todos trabalhando juntos para criar um sistema de registros de alunos bem encapsulado.
Experimente você mesmo
#include <iostream>
#include <string>
#include <sstream>
#include "Student.h"
int main() {
// Ler o nome do estudante
std::string name;
std::getline(std::cin, name);
// Ler o ID do estudante
std::string idStr;
std::getline(std::cin, idStr);
int studentId = std::stoi(idStr);
// Ler três notas de cursos (formato: "CourseName Score")
std::string line1, line2, line3;
std::getline(std::cin, line1);
std::getline(std::cin, line2);
std::getline(std::cin, line3);
// TODO: Analise cada linha para extrair o nome do curso e a nota
// Use std::stod() para converter as strings de notas em doubles
// TODO: Crie um objeto Student com o nome e o ID
// TODO: Adicione todas as três notas ao estudante
// TODO: Exiba o registro completo do estudante
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