Piattaforma di e-learning
Fa parte della sezione Programmazione orientata agli oggetti del percorso C++ di Coddy. Lezione 103 di 104.
Sfida
FacileCostruiamo una piattaforma di e-learning che riunisca tutti i concetti di OOP che hai imparato durante questo corso. Creerai un sistema che gestisce i corsi e diversi tipi di lezioni e tiene traccia dei progressi degli studenti, dimostrando come gerarchie di ereditarietà, polimorfismo, puntatori intelligenti e design pattern possano funzionare in armonia.
Organizzerai il codice in sei file:
User.h: crea una gerarchia di utenti con una classe baseUsere due classi derivate:StudenteInstructor.La classe base
Userdeve avere un nome e un ID, un metodo virtualegetRole()che restituisce il tipo di utente come stringa e un metodogetInfo()che restituisce"[name] ([id]) - [role]".La classe
Studenttiene traccia degli ID dei corsi a cui è iscritto (usa un vettore di stringhe) e del numero di lezioni completate. Aggiungi i metodienrollInCourse(const std::string& courseId),completedLesson()per incrementare il conteggio egetCompletedCount().La classe
Instructormemorizza una stringa che indica la specializzazione e tiene traccia degli ID dei corsi che insegna. AggiungiaddCourse(const std::string& courseId)egetSpecialty().Lesson.h: crea una gerarchia di lezioni usando una classe base astratta.La classe base
Lessondeve avere un titolo e una durata (in minuti), un metodo virtuale purocomplete()che restituisce un messaggio di completamento e un metodogetType()che restituisce il tipo di lezione.Crea tre classi derivate:
VideoLesson: ha un URL video. Il suo metodocomplete()restituisce"Watched video: [title]"QuizLesson: ha un numero di domande. Il suo metodocomplete()restituisce"Completed quiz: [title] ([questions] questions)"TextLesson: ha un conteggio di parole. Il suo metodocomplete()restituisce"Read article: [title]"
Ognuna deve ridefinire
getType()per restituire rispettivamente"Video","Quiz"o"Text".Course.h: crea una classeCourseche possiede le proprie lezioni usando puntatori intelligenti.Un corso ha un titolo, un ID e un ID dell'insegnante. Memorizza le lezioni come
std::vector<std::unique_ptr<Lesson>>, poiché il corso ne detiene la proprietà esclusiva.Aggiungi i metodi:
addLesson(std::unique_ptr<Lesson> lesson): trasferisce la proprietà della lezione al corsogetLessonCount(): restituisce il numero di lezionigetLesson(size_t index): restituisce un puntatore alla lezione in quell'indice (oppure nullptr se l'indice non è valido)displayCurriculum(): stampa il tipo e il titolo di ogni lezione nel formato"[index]. [Type]: [title]"
LessonFactory.h: implementa il pattern Factory per creare diversi tipi di lezione.Crea una classe
LessonFactorycon un metodo staticocreateLesson(const std::string& type, const std::string& title, int duration, const std::string& extra)che restituisce unstd::unique_ptr<Lesson>.Il parametro
typedetermina quale lezione creare ("video","quiz"o"text"). Il parametroextracontiene dati specifici del tipo: URL per il video, numero di domande per il quiz (da convertire in int) oppure conteggio di parole per il testo (da convertire in int).Platform.h: crea la classe centralePlatformche coordina ogni elemento.Memorizza i corsi come
std::vector<std::shared_ptr<Course>>e gli utenti comestd::vector<std::shared_ptr<User>>.Implementa:
addCourse(std::shared_ptr<Course> course)addUser(std::shared_ptr<User> user)findCourse(const std::string& id): restituisce un shared_ptr oppure nullptrfindUser(const std::string& id): restituisce un shared_ptr oppure nullptrenrollStudent(const std::string& studentId, const std::string& courseId): trova entrambi, iscrive lo studente e stampa"Enrolled [name] in [course title]"oppure"Enrollment failed"completeLesson(const std::string& studentId, const std::string& courseId, size_t lessonIndex): trova lo studente e il corso, chiama il metodo complete() della lezione, incrementa il conteggio delle lezioni completate dello studente e stampa il messaggio di completamento oppure"Could not complete lesson"
main.cpp: metti insieme tutti gli elementi per mostrare la tua piattaforma.Leggi quattro input:
- Nome della piattaforma
- Dettagli del corso (formato:
title,courseId,instructorId) - Dettagli dello studente (formato:
name,studentId) - Lezione da aggiungere (formato:
type,title,duration,extra)
Crea la piattaforma e visualizza
"Welcome to [platform name]!". Crea il corso e lo studente e aggiungili alla piattaforma. Usa LessonFactory per creare la lezione e aggiungerla al corso. Visualizza il programma del corso. Iscrivi lo studente al corso. Completa la prima lezione (indice 0) per quello studente. Infine, stampa le informazioni dello studente e il numero di lezioni completate nel formato"Completed lessons: [count]".
Ad esempio, con gli input CodeAcademy, C++ Mastery,CPP101,I001, Alice,S001 e video,Introduction to OOP,30,https://example.com/oop:
Welcome to CodeAcademy!
1. Video: Introduction to OOP
Enrolled Alice in C++ Mastery
Watched video: Introduction to OOP
Alice (S001) - Student
Completed lessons: 1Con gli input LearnHub, Python Basics,PY100,I002, Bob,S002 e quiz,Variables Quiz,15,10:
Welcome to LearnHub!
1. Quiz: Variables Quiz
Enrolled Bob in Python Basics
Completed quiz: Variables Quiz (10 questions)
Bob (S002) - Student
Completed lessons: 1Questa sfida mostra come sono strutturate le vere piattaforme di e-learning, con una chiara separazione tra utenti, contenuti e piattaforma che li coordina. Il pattern Factory rende flessibile la creazione delle lezioni, i puntatori intelligenti garantiscono una gestione sicura della memoria e il polimorfismo permette di trattare tutti i tipi di lezione in modo uniforme, pur consentendo a ciascuno di comportarsi in modo specifico.
Provalo tu
#include <iostream>
#include <string>
#include <sstream>
#include <memory>
#include "User.h"
#include "Lesson.h"
#include "Course.h"
#include "LessonFactory.h"
#include "Platform.h"
int main() {
// Leggi gli input
std::string platformName;
std::getline(std::cin, platformName);
std::string courseDetails; // formato: title,courseId,instructorId
std::getline(std::cin, courseDetails);
std::string studentDetails; // formato: name,studentId
std::getline(std::cin, studentDetails);
std::string lessonDetails; // formato: type,title,duration,extra
std::getline(std::cin, lessonDetails);
// TODO: Analizza courseDetails per estrarre title, courseId, instructorId
// TODO: Analizza studentDetails per estrarre name, studentId
// TODO: Analizza lessonDetails per estrarre type, title, duration, extra
// TODO: Crea la piattaforma e visualizza "Welcome to [platform name]!"
// TODO: Crea il corso e lo studente e aggiungili alla piattaforma
// TODO: Usa LessonFactory per creare la lezione e aggiungerla al corso
// TODO: Visualizza il programma del corso
// TODO: Iscrivi lo studente al corso
// TODO: Completa la prima lezione (indice 0) per lo studente
// TODO: Stampa le informazioni dello studente e il numero di lezioni completate
// Formato: "Completed lessons: [count]"
return 0;
}
Tutte le lezioni di Programmazione orientata agli oggetti
1Fondamenti della programmazione orientata agli oggetti
File esterniBuild e compilazione in C++File header e file sorgenteNamespace e ambitoIntroduzione alla programmazione orientata agli oggetti in C++Classi e oggetti a confrontoIl puntatore 'this'Metodi (funzioni membro)Attributi (membri dati)Fondamenti di costruttori e distruttoriRiepilogo - Calcolatrice semplice4Proprietà delle classi
Membri di istanza e staticiGetter e setterFunzioni membro constParola chiave mutableMetodi e variabili staticiFunzioni e classi friendRiepilogo - Gestore di conti bancari7Ereditarietà
Ereditarietà di baseLivelli di accesso nell’ereditarietàOrdine di chiamata di costruttori e distruttoriRidefinizione dei metodiFunzioni virtuali e VTableEreditarietà multiplaEreditarietà virtualeRiepilogo - Gerarchia dei dipendenti2Gestione della memoria
Memoria Stack vs HeapPuntatori e riferimentiMemoria dinamica (new/delete)Puntatori intelligenti in C++RAII in C++Riepilogo - Gestore di array dinamico5Incapsulamento
Specificatori di accesso in C++Specificatori di accesso in dettaglioOccultamento delle informazioniStruct vs classClassi annidate e interneRiepilogo - Sistema di registrazione degli studenti8Polimorfismo
Polimorfismo a compile time e a runtimeOverload delle funzioniFunzioni virtuali: ripassoFunzioni virtuali pureClassi astratteProgettazione delle interfacce in C++Dynamic casting e RTTIRipasso: calcolatrice di forme11Concetti avanzati di OOP
Composizione vs ereditarietàMixin tramite CRTPIdiom PimplType ErasureEnum class e tipizzazione forteGestione delle eccezioni in OOPGerarchie personalizzate di eccezioni14Pattern di progettazione - Parte 2
Pattern CommandPattern AdapterPattern DecoratorPattern Template MethodPattern StatePattern CompositeRAII come pattern3Costruttori e distruttori
Costruttore predefinitoCostruttore con parametriCostruttore di copiaCostruttore di spostamentoListe di inizializzazione dei costruttoriCostruttori delegantiApprofondimento sui distruttoriRegola del Tre / Cinque / ZeroRipasso - classe String6Sovraccarico degli operatori
Introduzione al sovraccarico degli operatoriSovraccarico degli operatori aritmeticiSovraccarico degli operatori di confrontoOperatori di flussoSovraccarico dell'operatore di assegnazioneSovraccarico degli operatori [] e ()Operatori di conversione di tipoRipasso - Classe Matrix9Template
Template di funzioneTemplate di classeSpecializzazione dei templateTemplate variadiciBasi di SFINAE e dei trait di tipoRiepilogo - Contenitore genericoEsercitati da solo: Compilatore C++ online