Riepilogo - Registri degli studenti
Fa parte della sezione Programmazione orientata agli oggetti del percorso GO di Coddy. Lezione 51 di 107.
Sfida
FacileCostruiamo un sistema di gestione dei record degli studenti che dimostri il corretto incapsulamento. Creerai una struttura per la gestione degli studenti in cui i dati accademici sensibili sono protetti, pur consentendo un accesso controllato tramite metodi ben progettati.
Organizzerai il codice in due file:
student.go: crea una strutturaStudentche protegge le informazioni sensibili ed espone al contempo i dati pubblici sicuri. Il campoNamedello studente deve essere esportato (accessibile pubblicamente), mentregrade(float64) estudentID(string) devono essere non esportati per proteggere queste informazioni sensibili.Implementa quanto segue:
- Un costruttore
NewStudent(name, id string, initialGrade float64) *Studentche crea uno studente. Il voto iniziale deve essere impostato solo se è compreso tra 0 e 100 (inclusi); altrimenti, imposta il valore predefinito a 0. - Un getter
Grade() float64che restituisce il voto attuale - Un getter
StudentID() stringche restituisce l'ID dello studente - Un setter
SetGrade(newGrade float64) boolche aggiorna il voto solo se il nuovo valore è compreso tra 0 e 100 (inclusi). Restituiscitruese il voto è stato aggiornato, altrimentifalse. - Un metodo
Summary() stringche restituisce il formato:[Name] (ID: [studentID]) - Grade: [grade]
- Un costruttore
main.go: leggi le informazioni dello studente dall'input, crea uno studente usando il costruttore, quindi esegui le operazioni sui voti. Visualizza il riepilogo dello studente dopo la creazione e dopo ogni tentativo di aggiornamento del voto.
Verranno forniti i seguenti input:
- Riga 1: nome dello studente
- Riga 2: ID dello studente
- Riga 3: voto iniziale
- Riga 4: primo nuovo voto da impostare
- Riga 5: secondo nuovo voto da impostare
Dopo aver creato lo studente, stampa il suo riepilogo. Poi prova ad aggiornare ciascun voto: se l'aggiornamento riesce, stampa il riepilogo aggiornato; se viene rifiutato, stampa Invalid grade rejected. Formatta tutti i voti con due cifre decimali.
Ad esempio, dati Emma Wilson, STU001, 85.5, 92.0 e 150, l'output dovrebbe essere:
Emma Wilson (ID: STU001) - Grade: 85.50
Emma Wilson (ID: STU001) - Grade: 92.00
Invalid grade rejectedL'ultimo aggiornamento non riesce perché 150 è fuori dall'intervallo valido. Il tuo metodo setter applica questa regola, mantenendo validi i dati dello studente. Nota che studentID e grade non sono mai accessibili direttamente: il codice esterno deve usare i metodi getter e setter per interagire con questi dati protetti.
Provalo tu
package main
import (
"bufio"
"fmt"
"os"
"strconv"
"strings"
)
func main() {
reader := bufio.NewReader(os.Stdin)
// Leggi il nome dello studente
name, _ := reader.ReadString('\n')
name = strings.TrimSpace(name)
// Leggi l'ID dello studente
id, _ := reader.ReadString('\n')
id = strings.TrimSpace(id)
// Leggi il voto iniziale
initialGradeStr, _ := reader.ReadString('\n')
initialGrade, _ := strconv.ParseFloat(strings.TrimSpace(initialGradeStr), 64)
// Leggi il primo nuovo voto
newGrade1Str, _ := reader.ReadString('\n')
newGrade1, _ := strconv.ParseFloat(strings.TrimSpace(newGrade1Str), 64)
// Leggi il secondo nuovo voto
newGrade2Str, _ := reader.ReadString('\n')
newGrade2, _ := strconv.ParseFloat(strings.TrimSpace(newGrade2Str), 64)
// TODO: Crea un nuovo studente usando il costruttore NewStudent
// TODO: Stampa il riepilogo dello studente dopo la creazione
// TODO: Prova ad aggiornare il voto per la prima volta
// Se l'aggiornamento riesce, stampa il riepilogo aggiornato
// Se l'aggiornamento viene rifiutato, stampa "Invalid grade rejected"
// TODO: Prova ad aggiornare il voto per la seconda volta
// Se l'aggiornamento riesce, stampa il riepilogo aggiornato
// Se l'aggiornamento viene rifiutato, stampa "Invalid grade rejected"
// Suggerimento: usa fmt.Sprintf con %.2f per formattare i voti in Summary()
_ = newGrade1 // Rimuovi questa riga quando usi la variabile
_ = newGrade2 // Rimuovi questa riga quando usi la variabile
}
Tutte le lezioni di Programmazione orientata agli oggetti
1Fondamenti di OOP in Go
File esterniWorkspace e moduli GoPacchetti e importazioniNomi esportati e non esportatiIntroduzione all’OOP in GoGli struct come classiDefinire metodi sugli structReceiver con puntatore vs receiver con valoreInizializzazione degli structFunzioni costruttriciRiepilogo - Calcolatrice semplice4Interfacce
Introduzione alle interfacceImplementazione implicitaL’interfaccia come contrattoInterfaccia vuota (any)Asserzione di tipoSwitch sul tipoComposizione di interfacceInterfacce Stringer ed ErrorRipasso - Calcolatore di forme7Incapsulamento
Campi esportati e non esportatiIncapsulamento a livello di packageMetodi Getter e SetterNascondimento delle informazioni in GoRiepilogo - Registri degli studenti10Tipi generici (Go 1.18+)
Introduzione ai tipi genericiParametri di tipoVincoli di tipoStruct genericheSoluzione alternativa per i metodi genericiRiepilogo - Collezione generica13Modelli di progettazione Parte 1
Introduzione ai modelli di progettazioneModello SingletonModello FactoryModello Abstract FactoryModello ObserverModello Strategy2Approfondimento su tipi e struct
Tipi di base e compostiDefinizioni di tipi personalizzatiTag delle structStruct anonimeStruct annidateValori zero e predefinitiRipasso - Rubrica5Composizione invece dell'ereditarietà
Perché Go non ha l'ereditarietàFondamenti dell'embedding delle structPromozione dei metodiEmbedding di più structEmbedding e aggregazione a confrontoMascheramento dei metodi embeddedRiepilogo: gerarchia dei dipendenti8Gestione degli errori e OOP
L'interfaccia errorTipi di errore personalizzatiWrapping degli errori (fmt.Errorf)Errori sentinellaerrors.Is() ed errors.As()Panic, Defer e RecoverRiepilogo - Parser di file11Libreria standard e OOP
io.Reader e io.Writersort.InterfaceInterfaccia fmt.Stringerencoding/json con le structInterfaccia http.HandlerRipasso - modelli REST API14Modelli di progettazione – Parte 2
Pattern CommandPattern AdapterPattern DecoratorPattern Template MethodPattern StatePattern CompositeMiddleware come Decorator3Puntatori e memoria
Concetti base dei puntatori in GoPuntatori a structPassaggio per valore vs per riferimentoLa funzione new()Garbage collection in GoRiepilogo - Costruttore di liste concatenate6Polimorfismo in Go
Polimorfismo tramite interfacceDuck typing in GoRegole di soddisfacimento delle interfacceCollezioni polimorficheIniezione delle dipendenzeRiepilogo - Elaboratore di pagamenti9Concorrenza e OOP
Basi delle goroutineCanali e comunicazioneCanali bufferizzati vs non bufferizzatiIstruzione selectsync.Mutex e sync.RWMutexsync.WaitGroupProgettazione di struct thread-safeRiepilogo: worker poolEsercitati da solo: Compilatore Go online