Riassunto Completo di Programmazione Orien-
tata agli Oggetti (OOP)
Prefazione
La Programmazione Orientata agli Oggetti (Object-Oriented Program-
ming, OOP) rappresenta una delle evoluzioni più significative nella storia
dell’informatica. Non è semplicemente un insieme di tecniche di program-
mazione, ma un vero e proprio paradigma, un modo di pensare e strutturare
il software che pone al centro i “dati” piuttosto che le “operazioni”. Questo
documento offre una trattazione completa e accademica dei principi fonda-
mentali dell’OOP, partendo dalle basi concettuali fino ad arrivare a principi
di progettazione avanzati come SOLID. L’obiettivo è fornire una guida solida
e approfondita per chiunque desideri comprendere e padroneggiare l’approccio
object-oriented, essenziale per lo sviluppo di software moderno, robusto e
manutenibile.
Capitolo 1: Dai Paradigmi Procedurali all’Orientamento
agli Oggetti
1.1 Paradigmi di Programmazione
Un paradigma di programmazione è uno stile fondamentale di programmazione,
un insieme di concetti e modelli che definiscono come i programmi vengono
strutturati e scritti.
• Programmazione Imperativa: Descrive come eseguire un compito at-
traverso una sequenza di comandi che modificano lo stato del programma.
• Programmazione Procedurale: È un’evoluzione della program-
mazione imperativa. Il codice è organizzato in procedure (o funzioni),
che raggruppano una serie di istruzioni per eseguire un compito specifico.
I dati e le procedure che operano su di essi sono tenuti separati. Questo
porta a una forte dipendenza dei dati globali, rendendo il software difficile
da modificare e manutenere al crescere della complessità.
1.2 I Limiti dell’Approccio Procedurale
Con l’aumentare delle dimensioni dei programmi, l’approccio procedurale
mostra i suoi limiti: * Scarsa Manutenibilità: Una modifica alla struttura
dei dati globali richiede di modificare tutte le procedure che accedono a tali
dati. * Bassa Riusabilità: È difficile riutilizzare una procedura in un altro
contesto se questa dipende strettamente da dati globali specifici. * Fragilità:
Il codice è fragile (“brittle”). Un piccolo cambiamento può avere effetti a
catena imprevedibili in tutto il programma.
1
1.3 L’Avvento dell’OOP
L’OOP nasce per superare questi limiti. L’idea centrale è di unire i dati e le
funzioni che operano su di essi in un’unica entità chiamata oggetto. Invece di
avere dati sparsi e procedure che li manipolano, abbiamo oggetti che contengono
i propri dati e offrono metodi per interagire con essi.
Vantaggi dell’Approccio OOP: * Modularità: Il software è composto da
oggetti autonomi e indipendenti, più facili da comprendere e gestire. * Infor-
mation Hiding: I dettagli interni di un oggetto sono nascosti al mondo esterno,
che può interagire con l’oggetto solo attraverso un’interfaccia pubblica. Questo
riduce le dipendenze e semplifica la manutenzione. * Riusabilità: Gli oggetti
e le classi possono essere facilmente riutilizzati in diversi progetti. * Estensi-
bilità: È possibile creare nuove classi a partire da quelle esistenti, ereditandone
le funzionalità e aggiungendone di nuove.
Capitolo 2: Classi e Oggetti: I Mattoni Fondamentali
2.1 Classi
Una classe è un “modello” o un “progetto” (blueprint) per creare oggetti.
Definisce un tipo di dato astratto, specificando: * Attributi (o Proprietà,
Membri): Le variabili che rappresentano lo stato di un oggetto. Sono i dati
che ogni oggetto di quella classe possiederà. * Metodi (o Operazioni): Le
funzioni che definiscono il comportamento di un oggetto. Sono le azioni che
un oggetto di quella classe può compiere.
Esempio: Una classe potrebbe avere attributi come
Automobile colore, marca,
e metodi come
velocita accelera(), frena(), accendi().
2.2 Oggetti
Un oggetto è un’istanza di una classe. Mentre la classe è il progetto, l’oggetto
è la sua realizzazione concreta in memoria. Ogni oggetto ha una propria identità,
un proprio stato (i valori dei suoi attributi) e un comportamento definito dalla
sua classe.
• Istanziazione: È il processo di creazione di un oggetto a partire da una
classe. Nella maggior parte dei linguaggi, si usa la parola chiave new.
// Creazione di due oggetti (istanze) della classe Automobile
new
Automobile miaAuto = Automobile();
new
Automobile autoDiGiovanni = Automobile();
e sono due oggetti distinti, ognuno con il proprio
miaAuto autoDiGiovanni
stato (potrebbero avere colori e velocità diverse).
2
Capitolo 3: I Quattro Pilastri dell’OOP
I principi fondamentali che definiscono un linguaggio come orientato agli oggetti
sono comunemente riassunti in quattro “pilastri”.
3.1 Incapsulamento (Encapsulation) e Information Hiding
L’incapsulamento è il meccanismo che lega insieme i dati (attributi) e il codice
che li manipola (metodi) all’interno di un oggetto.
L’information hiding è il principio secondo cui i dettagli implementativi di
un oggetto dovrebbero essere nascosti al mondo esterno. L’accesso allo stato
dell’oggetto è consentito solo attraverso un’interfaccia pubblica ben definita (i
suoi metodi pubblici).
Questo si ottiene tramite i modificatori di accesso: * Il membro
public:
(attributo o metodo) è accessibile da qualsiasi parte del codice. * Il
private:
membro è accessibile solo dall’interno della classe stessa. Questo è il livello di
visibilità raccomandato per gli attributi, per proteggere l’integrità dello stato
dell’oggetto. * Il membro è accessibile all’interno della classe, dalle
protected:
sue sottoclassi e, in alcuni linguaggi, dalle classi dello stesso package.
Getters e Setters: Per consentire un accesso controllato agli attributi privati,
si usano metodi pubblici specifici: * Metodi Getter: Restituiscono il valore di
un attributo (es. * Metodi Setter: Modificano il valore di un
getColore()).
attributo, potendo implementare logiche di validazione (es. setVelocita(int
potrebbe controllare che non sia negativa).
v) v
3.2 Ereditarietà (Inheritance)
L’ereditarietà è un meccanismo che permette di creare una nuova classe (detta
sottoclasse, classe derivata o classe figlia) a partire da una classe esistente
(detta superclasse, classe base o classe madre).
La sottoclasse eredita tutti gli attributi e i metodi (non privati) della super-
classe, e può: * Aggiungere nuovi attributi e metodi. * Sovrascrivere (Over-
ride) i metodi ereditati per fornire un’implementazione più specifica.
Questo crea una gerarchia “is-a” (è un). Esempio: una è
MacchinaSportiva
una Automobile.
• Vantaggi:
– Riuso del codice: Evita la duplicazione di codice, concentrando le
funzionalità comuni nella superclasse.
– Organizzazione gerarchica: Modella le relazioni tra concetti in
modo naturale.
• keyword: La parola chiave (o in C#) permette a una
super super base
sottoclasse di accedere ai membri (in particolare al costruttore) della sua
superclasse diretta. 3
3.3 Polimorfismo (Polymorphism)
Il polimorfismo (dal greco “molte forme”) è la capacità di un oggetto di assumere
più forme. In OOP, significa che un oggetto di una sottoclasse può essere trattato
come se fosse un oggetto della sua superclasse.
Questo permette di scrivere codice più generico e flessibile. Ad esempio, si
può creare una lista di e inserirvi oggetti di tipo
Automobile Automobile,
e Quando si chiama un metodo su un oggetto della
MacchinaSportiva SUV.
lista (es. verrà eseguita la versione del
auto.calcolaCostoAssicurazione()),
metodo specifica della classe effettiva dell’oggetto (MacchinaSportiva o SUV),
non quella della classe del riferimento (Automobile).
• Late Binding (o Dynamic Binding): La decisione su quale versione
di un metodo sovrascritto eseguire viene presa a runtime, in base al tipo
reale dell’oggetto, e non a compile-time. Questo è il meccanismo che rende
possibile il polimorfismo.
• Overloading vs. Overriding:
– Overriding (Sovrascrittura): Una sottoclasse ridefinisce un
metodo della superclasse. La firma del metodo (nome e parametri)
deve essere identica.
– Overloading (Sovraccarico): All’interno della stessa classe, si
definiscono più metodi con lo stesso nome ma con parametri diversi
(per numero o tipo).
3.4 Astrazione (Abstraction)
L’astrazione consiste nel nascondere la complessità implementativa e mostrare
solo le caratteristiche essenziali di un oggetto. In OOP, si realizza tramite classi
astratte e interfacce.
• Classe Astratta (Abstract Class): Una classe che non può essere
istanziata. Serve come modello base per altre classi. Può contenere sia
metodi concreti (con implementazione) sia metodi astratti (senza imple-
mentazione). Le sottoclassi sono obbligate a fornire un’implementazione
per tutti i metodi astratti ereditati.
• Interfaccia (Interface): È un “contratto” puramente astratto. Definisce
un insieme di metodi pubblici e astratti (e costanti). Una classe può im-
plementare un’interfaccia, impegnandosi a fornire un’implementazione
per tutti i metodi definiti dall’interfaccia. Un linguaggio come Java non
supporta l’ereditarietà multipla tra classi, ma una classe può implementare
più interfacce.
Le interfacce sono uno strumento potentissimo per ottenere un basso accoppi-
amento, permettendo a moduli diversi di comunicare attraverso un contratto
comune senza conoscere i dettagli delle rispettive implementazioni.
4
Capitolo 4: Progettazione Avanzata e Principi SOLID
I principi SOLID sono un insieme di cinque principi di progettazione orien-
tata agli oggetti che aiutano a creare software più comprensibile, flessibile e
manutenibile.
1. S - Single Responsibility Principle (SRP):
• Una classe dovrebbe avere una sola responsabilità, un solo motivo per
cambiare.
• Questo porta a classi più piccole, focalizzate e coese.
2. O - Open/Closed Principle (OCP):
• Le entità software (classi, moduli) dovrebbero essere aperte
all’estensione, ma chiuse alla modifica.
• Si dovrebbero poter aggiungere nuove funzionalità senza modificare
il codice esistente, tipicamente usando ereditarietà, polimorfismo e
astrazione (es. Strategy Pattern).
3. L - Liskov Substituti
-
Miei appunti Latex di Reti di calcolatori
-
Miei appunti Latex di Economia e organizzazione aziendale
-
Miei appunti presi con latex di Telecomunicazioni
-
Miei appunti personali presi con latex di Ricerca operativa