TOC

This article has been localized into Italian by the community.

Classi:

Funzioni locali

In articoli precedenti abbiamo appreso che i metodi e le proprietà appartengono alle classi in C #. All'interno dei metodi, puoi avere variabili locali, che sono variabili accessibili solo nell'ambito di questo metodo specifico. Questo ha senso perché spesso avrai dati temporanei che devi archiviare, ma che non dovrebbero essere accessibili da altre classi o anche da altri metodi nella stessa classe. In passato, non si poteva fare altrettanto con i metodi: l'accesso ad un metodo dichiarato in una classe era consentito, al minimo, all'interno di un metodo della stessa classe, ma nella versione 7 di C# è stato introdotto il concetto di funzione locale.

Una funzione locale è dichiarata all'interno di un metodo esistente ed è accessibile solo da questo metodo. Questo incapsula la funzionalità molto strettamente e rende anche chiaro a tutti i lettori del codice che questa funzionalità è rilevante solo per il metodo di dichiarazione. Una funzione locale si presenta come un metodo normale, ma senza il modificatore di visibilità, perché una funzione locale è sempre accessibile solo all'interno del metodo di dichiarazione. Ecco un esempio:

public void MethodWithLocalFunction()
{
	bool doesNameStartWithUppercaseChar(string name)
	{
		if(String.IsNullOrEmpty(name))
			throw new Exception("name parameter must contain a value!");
		return Char.IsUpper(name[0]);
	}

	List<string> names = new List<string>()
	{
		"john doe",
		"Jane doe",
		"dog Doe"
	};

	foreach(string name in names)
		Console.WriteLine(name + " starts with uppercase char: " + doesNameStartWithUppercaseChar(name));
}

Un esempio abbastanza stupido, ma che dimostra come puoi dichiarare una funzione locale (in questo caso chiamate doesNameStartWithUppercaseChar) dentro un metodo (chiamato MethodWithLocalFunction) e poi chiamarlo una o parecchie volte dall'interno di un metodo.

Come puoi vedere nel mio esempio, dichiaro la funzione locale all'inizio del metodo. Sei libero di cambiarlo, ad esempio dichiarandolo a metà o alla fine del metodo. Solo in un caso farà la differenza: a una funzione locale è consentito accedere alle variabili dichiarate all'interno del metodo di dichiarazione, ma solo se sono state dichiarate prima della funzione locale. Quindi, se vuoi sfruttare questo comportamento, dovrai modificare il metodo, ad esempio come questo:

public void MethodWithLocalFunction()
{
	int nameMaxLength = 10;

	List<string> names = new List<string>()
	{
		"john doe",
		"Jane doe",
		"dog Doe"
	};

	foreach(string name in names)
		Console.WriteLine(name + " starts with uppercase char: " + doesNameStartWithUppercaseChar(name));

	bool doesNameStartWithUppercaseChar(string name)
	{
		if(String.IsNullOrEmpty(name))
			throw new Exception("name parameter must contain a value!");
		if(name.Length > nameMaxLength)
			throw new Exception("name is too long! Max length: " + nameMaxLength);
		return Char.IsUpper(name[0]);

	}
}

Si noti come dichiaro la variabile nameMaxLength all'interno del metodo e quindi accedo ad essa all'interno della funzione locale.

Funzione statica locale

In C # versione 8, è stato aggiunto il supporto per funzioni locali statiche . Al momento della scrittura, l'unica differenza tra una regolare una funzione statica locale è il fatto che una funzione locale statica non può utilizzare le variabili del metodo dichiarante - in altre parole, non condividono più lo scope. Quindi, se vuoi assicurarti che la tua funzione locale non possa fare riferimento o cambiare variabili dal metodo, dichiarala come statica, in questo modo:

public void MethodWithLocalStaticFunction()
{
	int nameMaxLength = 10;
	
	static bool doesNameStartWithUppercaseChar(string name)
	{
		// Local variables, e.g. nameMaxLength, are no longer accessible here....
		if(String.IsNullOrEmpty(name))
			throw new Exception("name parameter must contain a value!");
		return Char.IsUpper(name[0]);
	}
	....
}

Sommario

In alcune situazioni, le funzioni locali possono essere un grande aiuto quando hai bisogno di incapsulare e riusare delle specifiche funzionalità. In alternativa se la funzionalità può essere riutilizzata da altri metodi, è consigliabile prendere in considerazione l'aggiunta come metodo reale su una classe di supporto o come metodo di estensione.


This article has been fully translated into the following languages: Is your preferred language not on the list? Click here to help us translate this article into your language!