Passaggio dei paramettri

Passaggio per valore

Si ha un passaggio di parametri per valore quando, alla chiamata di un metodo nel main, passi una copia di uno o più valori che all'interno del metodo chiamato possono essere modificate. Essendo però copie dei valori, non manterranno le modifiche esternamente.

Passaggio per riferimento

Si ha un passaggio di parametri per riferimento quando, alla chiamata di un metodo nel main, passi il riferimento a uno o più valori. Questo significa che all'interno del metodo chiamato possono essere modificati i valori che sono riferiti, e le modifiche avvengono in modo "sequenziale".

Passaggio per valore-risultato (value-result)

Si ha un passaggio di parametri per valore-risultato (o value-result) quando anche la funzione (o porcedura) chiamante riceve un valore. Ossia, il valore del parametro attuale viene copiato nel parametro formale della funzione chiamata che, al termine della sua esecuzione, manda la copia del valore del parametro formale al parametro attuale della funzione chiamata. In sostanza, è molto simile al passaggio per riferimento (ovvero il valore cambia da entrambe le parti) ma non si ha aliasing (ossia più nomi che "puntano" alla stessa locazione di memoria). Una differenza sostanziale è però che nel passaggio per riferimento il valore viene mutato immediatamente dopo l'istruzione, mentre nel passaggio per value-result il valore viene mutato solo al termine dell'esecuzione della funzione (o procedura).

Esempio:
void addUno(int x){
	x = x + 1; //prende 9, gli aggiunge 1 e manda il risultato al parametro attuale nel main
}


void main(){
	addUno(9); //y=9 al momento della chiamata, y=10 quando l'esecuzione di addUno termina
}

Passaggio per nome

Molto simile al passaggio di parametri per riferimento, con la differenza che i parametri attuali (e quindi nella chiamata nel main) vengono modificati via via, quindi è una sorta di modifica "simultanea" dei valori utilizzati.
Esempio:

int i = 2;
void foo(int f, int g) {
	f = f - i;
	g = f;
}
int main( ) {
	int a[] = {2, 0, 1};
	//alla chiamata di foo, i=2 e a[i] non sarà a[2] bensì a[0] perchè i varia. 
	//Quindi accade che 2 diventa 0, a[0] diventa 0 e a[1] e a[2] restano invariate
	foo(i, a[i]);
	printf("%d %d %d %d\n", i, a[0], a[1], a[2]);
	//l'output con il passaggio per nome sarà infatti 0 0 0 1
}