/* Pensate a come risolvere questo problema: dobbiamo sommare 3 coppie di
* variabili di 3 tipi diversi: int,long,float. In C occorre scriversi 3
* funzioni di somma, una per gli int, una per i long, e una per i float:
*
* int sommainteri(int a,int b) {...}
* long sommalong(long c,long d) {...}
* float sommafloat(float e,float f) {...}
*
* In seguito, nel programma, dobbiamo stare attenti ad usare la funzione
* giusta a seconda del tipo da sommare:
*
* bau = sommafloat(miofloat1,miofloat2);
* beu = sommalong(miolong1,miolong2);
* bou = sommaint(mioint1,mioint2);
*
* Se poi le mie variabili si chiamano sbirulino, scarrafone, ecc., dovro'
* anche andarmi a cercare ogni volta nel listato la dichiarazione per
* ricordarmi il loro tipo, per usare la funzione giusta.
* In C++, invece, grazie al polimorfismo, possiamo sovrapporre metodi
* aventi lo stesso nome, purche' abbiano parametri diversi: in questo
* modo, possiamo riscrivere i 3 metodi visti prima dandogli lo stesso nome:
*
* int somma(int a,int b) {...}
* long somma(long c,long d) {...}
* float somma(float a,float b) {...}
*
* Questa sovrapposizione (overloading), ci permette ora di scrivere in
* modo molto piu' semplice il listato, usando somma() per tutti i casi:
*
* bau = somma(miofloat1,miofloat2);
* beu = somma(miolong1,miolong2);
* bou = somma(mioint1,mioint2);
*
* Questo approccio e' migliore dal punto di vista logico, infatti quando
* programmiamo e sommiamo la variabile X con la variabile Y, spesso non
* ci ricordiamo il tipo di queste ultime, non essendo fondamentale, ma
* se dobbiamo usare funzioni diverse a seconda del tipo, allora siamo
* costretti a far entrare nel nostro ragionamento anche questo, facendoci
* distrarre. Se dovessimo usare degli operatori diversi a seconda del
* tipo di numeri anche quando facciamo i conti a mente, ad esempio dovessimo
* pensare: "1 piuintero 1 = 2", "1.00 piufloat 1.00 = 2.00", "1 menointero
* 1 = 0", "1.00 menofloat 1.00 = 0.00", "1 perintero 1 = 1", "1.00 perfloat
* 1.00 = 1.00", "1 divisointero 1 = 1", "1.00 divisofloat 1.00 = 1.00",
* allora fare i conti della spesa diventerebbe difficile anche per un
* professore di matematica.
* Invece, grazie al polimorfismo, si puo' "scaricare" questo compito al
* compilatore, lasciando a noi i problemi piu' seri.
* Da notare che il tipo di valore restituito dal metodo (ritorno) non
* conta quando il compilatore deve scegliere che overload chiamare: per
* tale scopo sono presi in considerazione solo i parametri in entrata.
*
* Vediamo questo esempio:
*/
#include <iostream.h> // Header necessario per usare CIN e COUT
// Questo e' un commento C++ ad una sola linea
/* Ecco i 3 metodi aventi lo stesso nome e parametri diversi, che grazie
* al polimosfismo si overloadano (soprappongono): ogni volta verra'
* chiamato automaticamente il metodo giusto a seconda del tipo.
*/
int somma(int a,int b)
{
return(a+b);
}
// Ora la versione per i long
long somma(long c,long d)
{
return(c+d);
}
// Infine la versione per i float
float somma(float e,float f)
{
return(e+f);
}
///////////////////////////////////////////////////////////////////////////
// Il main...
///////////////////////////////////////////////////////////////////////////
int main(void)
{
int mioint1 = 15; // Variabile di tipo int
int mioint2 = 50; // Variabile di tipo int
long miolong1 = 150000; // variabile di tipo long
long miolong2 = 1666000; // variabile di tipo long
float miofloat1 = 3.02; // Variabile di tipo float
float miofloat2 = 32.24; // Variabile di tipo float
// Ora sommiamo coppie di variabili di 3 tipi diversi usando sempre somma()
cout << mioint1 << " + " << mioint2 << " = ";
cout << somma(mioint1,mioint2) << "\n";
cout << miolong1 << " + " << miolong2 << " = ";
cout << somma(miolong1,miolong2) << "\n";
cout << miofloat1 << " + " << miofloat2 << " = ";
cout << somma(miofloat1,miofloat2) << "\n";
return 0; // main() restituisce 0
}
/* L'overloading permette di accedere ad un unsieme di metodi simili (almeno
* a livello logico) usando lo stesso nome.
* Naturalmente un'altra comodita' del polimorfismo e' quella di aggiungere
* dei parametri opzionali ad una funzione, ad esempio si puo' fare in
* modo che un metodo "mettiorario" possa accettare l'ora sia come 3 interi,
* ore,minuti,secondi, che come stringa di testo "HH:MM:SS", che come un
* singolo intero che rappresenti il numero di secondi passati dalle 00:00,
* e opzionalmente si possa immettere un testo. I casi possibili saranno:
*
* mettiorario(16,28,5);
* mettiorario("16:28:05");
* mettiorario(58805);
* mettiorario(16,28,5, "oggi sono contento");
* mettiorario("16:20:05", "oggi sono contento");
* mettiorario(58805, "oggi sono contento");
*
* Come si vede, 6 funzioni tutte con lo stesso nome. La sua documentazione
* sarebbe qualcosa di simile:
*
* -------------------------------------------------------------------------
* mettiorario(ora, messaggio opzionale)
*
* ora = uno di questi 3 formati:
*
* int,int,int ; ore, minuti, secondi
* "HH:MM:SS" ; stringa
* long ; n. secondi dall'inizio del giorno.
* -------------------------------------------------------------------------
*
* Il tutto e' molto semplice. Immaginatevi a dover documentare cio' con
* 6 funzioni di nome diverso a seconda dei parametri da passare!
*/
