In C++ una variabile può essere globale o locale. Una variabile globale può essere vista e modificata da tutte le funzioni del programma, mentre una variabile locale è visibile solo all interno della funzione che la dichiara. In questa lezione vedremo perché lasciare una variabile visibile a tutto il programma può essere rischioso e come l utilizzo dei puntatori permetta di controllare l accesso ai dati in modo più sicuro.
1️⃣ Cos è una variabile globale
Una variabile globale è dichiarata fuori da tutte le funzioni. Tutte le parti del programma possono leggerla e modificarla senza alcuna limitazione.
int crediti = 500; // variabile globale
void bonus() { crediti += 100; }
void penalita(){ crediti -= 50; }
2️⃣ Problemi reali delle variabili globali
- Difficile fare debug: il valore può cambiare da qualsiasi funzione.
- Codice fragile: un reset o una modifica inattesa può rompere la logica del programma.
- Funzioni non riutilizzabili: dipendono dalla globale e non possono essere usate altrove.
- Perdita di controllo: non puoi decidere quali funzioni possono modificare il dato.
- Accesso incontrollato: tutte le funzioni possono leggere e scrivere la variabile.
3️⃣ La variabile locale e il puntatore
Una variabile locale vive dentro una funzione (ad esempio il main).
Altre funzioni non possono vederla, a meno che tu non gli passi un puntatore.
void bonus(int* p) {
*p += 100; // modifica il valore originale
}
int main() {
int crediti = 500; // ora è locale
bonus(&crediti); // solo la funzione bonus può modificarla
}
4️⃣ Globale vs Puntatore: differenza fondamentale
| Variabile Globale | Variabile Locale + Puntatore |
|---|---|
| Visibile da tutto il programma | Visibile solo nella funzione proprietaria |
| Tutte le funzioni possono modificarla | Solo chi riceve il puntatore può modificarla |
| Rende il codice fragile | Maggiore sicurezza e controllo |
| Difficile da debuggare | Ogni modifica è tracciabile |
LABORATORIO
Simulazione ATM con Operazioni Casuali
In questo laboratorio simulerai il funzionamento di un bancomat.
Il programma genererà 50 operazioni casuali (prelievo o versamento),
ciascuna con un importo compreso tra 50€ e 500€.
Le operazioni verranno memorizzate in un vettore di struct e al termine
verrà mostrato il saldo finale e un report completo.
Attenzione: non utilizzare variabili globali. Tutti i dati devono
essere gestiti tramite variabili locali e passati alle funzioni tramite puntatori.
- Ambiente di sviluppo C++
- Funzione
rand()per generare numeri casuali - Struct e vettori
1 Preparazione: struttura dell operazione
Ogni operazione deve contenere: tipo (prelievo/versamento), importo utilizzato e saldo dopo l operazione. Crea una struct chiamata Operazione:
struct Operazione {
string tipo;
int importo;
int saldoDopo;
};
Il programma utilizzerà un vettore di 50 elementi di questa struct:
Operazione storico[50];
2 Saldo iniziale e regole del bancomat
Il saldo parte da 1000€. Le operazioni devono rispettare queste regole:
- Importo compreso tra 50 e 500
- Se l operazione è un prelievo e il saldo è insufficiente, l operazione deve essere negata
- Ogni operazione va salvata nel vettore
int saldo = 1000; // variabile locale
saldo come variabile globale.
Le funzioni devono riceverlo tramite puntatore.
3 Uso di rand()
La funzione rand() genera numeri casuali.
Per ottenere un numero da 50 a 500:
int importo = 50 + rand() % 451; // (500 - 50 + 1) = 451
Per scegliere il tipo di operazione:
int scelta = rand() % 2; // 0 = prelievo, 1 = versamento
4 Funzioni: prelievo e versamento
Crea due funzioni che modificano il saldo tramite puntatore e salvano l operazione effettuata.
void prelievo(int* saldo, int importo, Operazione& op) {
if (*saldo >= importo) {
*saldo -= importo;
op.tipo = "Prelievo";
op.importo = importo;
op.saldoDopo = *saldo;
} else {
op.tipo = "Prelievo NEGATO";
op.importo = importo;
op.saldoDopo = *saldo;
}
}
void versamento(int* saldo, int importo, Operazione& op) {
*saldo += importo;
op.tipo = "Versamento";
op.importo = importo;
op.saldoDopo = *saldo;
}
5 Ciclo principale delle 50 operazioni
Ora crea il ciclo che esegue 50 operazioni casuali.
for (int i = 0; i < 50; i++) {
int importo = 50 + rand() % 451;
int scelta = rand() % 2; // 0 = prelievo, 1 = versamento
if (scelta == 0) {
prelievo(&saldo, importo, storico[i]);
} else {
versamento(&saldo, importo, storico[i]);
}
}
6 Report finale
Stampa tutte le operazioni effettuate e il saldo finale:
for (int i = 0; i < 50; i++) {
cout << i+1 << ") "
<< storico[i].tipo << " - "
<< storico[i].importo << "€"
<< " | Saldo dopo: " << storico[i].saldoDopo << "€"
<< endl;
}
cout << "\nSALDO FINALE: " << saldo << "€" << endl;