Funzione (informatica): differenze tra le versioni
Contenuto cancellato Contenuto aggiunto
→Descrizione: Rimossa trattazione di alcuni concetti superflui |
Nessun oggetto della modifica Etichette: Modifica visuale Modifica da mobile Modifica da web per mobile |
||
(6 versioni intermedie di 2 utenti non mostrate) | |||
Riga 11:
* un identificativo o nome;
* per [[Tipizzazione forte|linguaggi tipizzati]] un [[tipo di ritorno]] ovvero una specifica sul [[tipo di dato]] che essa restituirà in output all'utente o ad altre funzioni che la invocano; quando una funzione non restituisce nulla (
* la specifica (non sempre necessaria) dei cosiddetti [[Parametro (programmazione)|parametri]] o
* il corpo della funzione ovvero il nucleo dell'elaborazione costituita dal blocco, opportunamente delimitato, di una o più istruzioni, ciascuna terminata dal comando di terminazione, [[iterazione|cicli iterativi]], [[selezione (informatica)|strutture condizionali]] ecc., il tutto concluso con la variabile eventualmente ritornata in output. Variabili definite nel blocco saranno necessariamente variabili locali cioè con visibilità solo all'interno del blocco stesso.
=== Identificatore ===
{{Vedi anche|Funzione anonima|Overloading}}
Una funzione è una porzione di codice che può essere invocata da qualsiasi punto di un programma. Per l'invocazione occorre tipicamente richiamarne almeno il nome passando i valori degli eventuali parametri, cui si aggiungono eventualmente altri dettagli dipendenti dal particolare linguaggio di programmazione in uso.
=== Parametri ===
Generalmente i parametri di una funzione sono definiti all'atto della definizione della stessa. La loro numerosità e il loro ordine è fissato.
Alcuni linguaggi forniscono sistemi più o meno eleganti per realizzare funzioni con un numero variabile di argomenti. In tal caso la funzione si dice "variadica".<ref>{{Cita web|url=http://wpage.unina.it/benerece/LASD-2017/5-Funzioni-a-parametri-variabili.pdf|titolo=Funzioni con numero variabile di parametri: Funzioni Variadiche in C|autore=Massimo Benerecetti|sito=unina.it|accesso=24 marzo 2022|urlarchivio=https://web.archive.org/web/20190711182550/http://wpage.unina.it/benerece/LASD-2017/5-Funzioni-a-parametri-variabili.pdf|urlmorto=no|dataarchivio=11 luglio 2019}}</ref>
Nei [[linguaggio tipizzato|linguaggi tipizzati]], anche il [[tipo di dato]] dei parametri formali deve essere definito,
==== Parametri formali ed effettivi ====
Le variabili della funzione che fanno riferimento ai parametri ricevuti sono detti parametri formali.
Quando una funzione viene invocata, gli identificatori associati internamente ai valori che le vengono passati sono detti parametri effettivi o
▲Quando una funzione viene invocata, gli identificatori associati internamente ai valori che le vengono passati sono detti parametri effettivi o ''parametri attuali''.
▲Nei [[linguaggio tipizzato|linguaggi tipizzati]], anche il [[tipo di dato]] dei parametri formali deve essere definito, ed il [[type checking]] deve essere svolto anche per verificare che i parametri effettivi siano di tipo compatibile con quello dei corrispondenti parametri formali. Il tipo di un parametro può essere anche una complessa [[struttura dati]].
Ciascuna istanza di una funzione che è in esecuzione in un certo momento possiede la propria copia dei parametri effettivi (e delle variabili locali).
==== Passaggio dei parametri ====
Il comportamento di una funzione può essere dipendente dai dati che le sono passati come parametri all'atto dell'invocazione; inoltre una funzione può restituire un dato all'uscita.
Esistono diverse modalità di passaggio dei parametri, o di accesso alle strutture definite all'interno del programma stesso: ogni linguaggio, infatti, gestisce il proprio [[ambiente (programmazione)|ambiente]] dipendentemente dalle [[Variabile (informatica)#Visibilità di una variabile|regole di ''scoping'']] che implementa, e di cui è necessario tenere conto.
Con questo meccanismo il valore del parametro effettivo viene copiato nella variabile della funzione chiamata che rappresenta il parametro formale. Se la funzione chiamata lo modifica, la funzione chiamante non potrà vedere questa modifica. Si tratta quindi di un passaggio unidirezionale.
Con questo meccanismo la funzione invocata riceve come parametro un [[puntatore (programmazione)|puntatore]] o riferimento al parametro effettivo. Se si modifica il parametro passato per indirizzo, la modifica sarà visibile anche alla funzione chiamante. Il passaggio è quindi potenzialmente bidirezionale.
=== Valore di ritorno ===
Una funzione può restituire un valore ([[tipo di dato|tipizzato]]) al chiamante. Questa modalità di passaggio di dati è unidirezionale, dal chiamato al chiamante.
Riga 61 ⟶ 57:
== Implementazione ==
=== Supporto nei linguaggi di programmazione ===
Il concetto di funzione è utilizzabile in tutti i [[linguaggi di programmazione]] che implementano il [[programmazione procedurale|paradigma procedurale]].
La maggioranza dei [[linguaggio di programmazione ad alto livello|linguaggi di programmazione ad alto livello]] supporta esplicitamente le funzioni, prevedendo costrutti sintattici dedicati o che in alternativa accorpano diverse varianti del concetto:
* i linguaggi influenzati dal [[C (linguaggio di programmazione)|
* nei linguaggi fortemente [[programmazione orientata agli oggetti|orientati agli oggetti]],
{{Cita web|url=https://www.w3schools.com/java/java_methods.asp|titolo=Java Methods|accesso=2024-03-25|lingua=en}}</ref><ref>{{Cita web|url=https://docs.oracle.com/javase/tutorial/java/javaOO/methods.html|titolo=Defining Methods|accesso=2024-03-25|lingua=en}}</ref>
* nei [[IEC 61131-3|linguaggi per l'automazione industriale]] le funzioni sono disponibili anche sotto forma di
▲* nei [[IEC 61131-3|linguaggi per l'automazione industriale]] le funzioni sono disponibili anche sotto forma di "[[Function block diagram|blocchi funzionali]]".<ref>{{Cita|Basile, Chiacchio 2004|cap. 2.3}}.</ref>
Alcuni linguaggi tendono
* il termine subroutine è stato usato fino dagli albori della [[programmazione (informatica)|programmazione]] per riferirsi a sezioni di codice [[Linguaggio assembly|assembly]] o in [[linguaggio macchina]] (e viene usato per estensione in altri contesti ad esempio nelle prime versioni del [[BASIC]]);
Riga 100 ⟶ 82:
In [[assembly]] esistono istruzioni dedicate al supporto delle funzioni e dello stack, con un corrispondente diretto nel linguaggio macchina:
* {{Codice|codice=PUSH|linguaggio=asm}}: metti un valore sullo [[Pila (informatica)|stack]]
* {{Codice|codice=POP|linguaggio=asm}}: leggi e togli dallo stack un valore
* {{Codice|codice=JSR|linguaggio=asm}}: ''jump to subroutine'', ovvero salta
* {{Codice|codice=RET|linguaggio=asm}}: ritorno da una subroutine al chiamante (identificato eseguendo una {{Codice|codice=POP|linguaggio=asm}} dell'indirizzo di ritorno dallo stack)
Naturalmente, ciascuna funzione o pezzo di codice che usa lo stack ha la responsabilità di togliere tutto quello che ha messo sullo stack prima di terminare (e nulla più di quanto ha messo), altrimenti il valore di un parametro o di una variabile locale verrà impiegato come indirizzo di ritorno, con conseguenze impredicibili. La difficoltà di garantire manualmente questa correttezza è uno dei motivi che giustificano l'uso di [[Linguaggio di programmazione ad alto livello|linguaggi di alto livello]], che tra l'altro gestiscono automaticamente la coerenza dello stack.
Riga 110 ⟶ 92:
== Utilizzi ==
=== Riuso
{{Vedi anche|Riuso di codice}}
Una funzione dovrebbe eseguire una determinata operazione o risolvere un determinato problema (o al limite tutto il problema) all'interno dell'[[algoritmo]] risolutivo, contribuendo così alla [[fattorizzazione (software)|fattorizzazione]] del [[software]]. Ad esempio, una subroutine progettata per disporre in ordine crescente un insieme di numeri interi può essere richiamata in tutti i contesti in cui questa operazione sia utile o necessaria, e supplisce alla mancanza di una vera e propria "istruzione" dedicata allo scopo, consentendo al contempo di descrivere il corrispondente [[algoritmo di ordinamento]] in un unico punto del programma.
Riga 117 ⟶ 100:
=== Hacking ===
{{Vedi anche|Arbitrary code execution}}
Il meccanismo di implementazione delle funzioni, insieme all'aritmetica dei puntatori nel [[linguaggio C]], viene sfruttato per costruire attacchi di tipo ''[[stack overflow]]'' o ''[[buffer overflow]]'', che permettono di prendere il controllo di un programma in esecuzione fornendogli dati accuratamente artefatti.
Riga 124 ⟶ 108:
== Bibliografia ==
* {{Cita libro|autore=[[Brian W. Kernighan]]|autore2=[[Dennis M. Ritchie]]|traduttore=Valerio Marra|titolo=Il linguaggio C|edizione=2|editore=Pearson|anno=2007|ISBN=978-88-7192-200-3|cid= K&R 2007}}
* {{Cita libro|titolo=Tecnologie informatiche per l'automazione|autore=Francesco Basile|autore2=Pasquale Chiacchio|edizione=2|editore=McGraw-Hill|città= Milano|anno=2004|ISBN=88-386-6147-2|cid= Basile, Chiacchio 2004}}
== Voci correlate ==
{{Div col}}
* [[Punto d'ingresso]]
* [[Funzione variadica]]
Riga 158 ⟶ 123:
* [[Pila (informatica)]]
* [[Macro (informatica)]]
{{Div col end}}
== Altri progetti ==
|