Cosa ha innescato la popolarità delle funzioni lambda nei moderni linguaggi di programmazione mainstream?


112

Negli ultimi anni le funzioni anonime (funzioni AKA lambda) sono diventate un costrutto linguistico molto popolare e quasi tutti i principali linguaggi di programmazione mainstream li hanno introdotti o sono previsti per introdurli in una prossima revisione dello standard.

Tuttavia, le funzioni anonime sono un concetto molto antico e molto noto in Matematica e Informatica (inventato dal matematico Alonzo Church intorno al 1936 e utilizzato dal linguaggio di programmazione Lisp dal 1958, vedi ad esempio qui ).

Quindi perché i linguaggi di programmazione tradizionali di oggi (molti dei quali originati da 15 a 20 anni fa) non supportavano le funzioni lambda sin dall'inizio e le hanno introdotte solo in seguito?

E cosa ha innescato l'adozione massiccia di funzioni anonime negli ultimi anni? C'è qualche evento specifico, nuovo requisito o tecnica di programmazione che ha iniziato questo fenomeno?

NOTA IMPORTANTE

Il focus di questa domanda è l'introduzione di funzioni anonime nei linguaggi moderni, principali (e quindi, forse con alcune eccezioni, non funzionali). Si noti inoltre che in Smalltalk sono presenti funzioni anonime (blocchi), che non è un linguaggio funzionale, e che le funzioni con nomi normali sono presenti da molto tempo anche in linguaggi procedurali come C e Pascal.

Per favore, non generalizzare troppo le tue risposte parlando di "l'adozione del paradigma funzionale e dei suoi benefici", perché questo non è l'argomento della domanda.


7
15-20 anni fa la gente faceva la stessa domanda su OO ... non era un nuovo concetto ma aveva un'esplosione di popolarità.
MattDavey,

7
@MattDavey La maggior parte non sarebbe certamente d'accordo, ma poi dovrei ricordare loro che "la maggior parte degli sviluppatori Smalltalk" non è poi così tante persone; P
yannis,

30
Penso che la domanda più interessante sia cosa abbia scatenato la loro scomparsa ! Dopo tutto, c'è stato un tempo, quando la maggior parte delle lingue moderne hanno fatto avere lambda, poi linguaggi come Java e C ++ è diventato popolare. (Anche se non chiamerei esattamente Java un linguaggio "moderno". Il concetto più moderno in Java è Generics, che risale alla fine degli anni '60 / primi anni '70. Anche la combinazione di funzionalità fornite da Java, sicurezza dei puntatori, sicurezza della memoria, tipo safety, GC, OO tipicamente statico, tutti i generici esistevano a Eiffel nel 1985 ... e molto meglio, IMHO.)
Jörg W Mittag

31
Anche prima che uscisse Java 1.0, mentre era ancora nelle prime fasi di progettazione, praticamente tutti hanno sottolineato che Java ha bisogno di lambda. Alcuni dei designer che hanno lavorato su Java includono Guy Steele (proponente di Lisp, co-designer di Scheme, co-autore di Common Lisp, designer di Fortress), James Gosling (autore del primo interprete di Emacs Lisp per PC), Gilad Bracha (Smalltalk proponente, co-designer di Animorphic Smalltalk, designer di Newspeak), Phil Wadler (co-designer di Haskell), Martin Odersky (designer di Scala). Come Java sia finito senza lambdas è davvero al di là di me.
Jörg W Mittag,

8
"Un po '" spesso significa funzione al 50%, rumore al 50%.
Kevin Cline,

Risposte:


86

C'è sicuramente una tendenza evidente verso la programmazione funzionale, o almeno alcuni aspetti di essa. Alcune delle lingue popolari che ad un certo punto hanno adottato funzioni anonime sono C ++ ( C ++ 11 ), PHP ( PHP 5.3.0 ), C # ( C # v2.0 ), Delphi (dal 2009), Obiettivo C ( blocchi ) mentre Java 8 porterà il supporto per lambdas nella lingua . E ci sono lingue popolari che generalmente non sono considerate funzionali ma supportano funzioni anonime dall'inizio, o almeno all'inizio, l'esempio brillante è JavaScript.

Come per tutte le tendenze, cercare di cercare un singolo evento che li abbia stimolati è probabilmente una perdita di tempo, di solito è una combinazione di fattori, molti dei quali non sono quantificabili. Practical Common Lisp , pubblicato nel 2005, potrebbe aver avuto un ruolo importante nel portare nuova attenzione a Lisp come linguaggio pratico , poiché per un po 'di tempo Lisp era principalmente una lingua che avresti incontrato in un ambiente accademico o mercati di nicchia molto specifici. La popolarità di JavaScript potrebbe anche aver giocato un ruolo importante nel portare nuova attenzione alle funzioni anonime, come spiega munificent nella sua risposta .

Oltre all'adozione di concetti funzionali da linguaggi multiuso, c'è anche un notevole spostamento verso linguaggi funzionali (o principalmente funzionali). Lingue come Erlang (1986), Haskell (1990), OCaml (1996), Scala (2003), F # (2005), Clojure (2007) e persino lingue specifiche del dominio come R (1993) sembrano aver guadagnato un forte seguito fortemente dopo che furono introdotti. La tendenza generale ha portato nuova attenzione ai linguaggi funzionali più vecchi, come Scheme (1975) e ovviamente Common Lisp.

Penso che il singolo evento più importante sia l'adozione della programmazione funzionale nel settore. Non ho assolutamente idea del perché non fosse così, ma mi sembra che ad un certo punto all'inizio e alla metà degli anni '90 la programmazione funzionale abbia iniziato a trovare il suo posto nel settore, a partire (forse) dalla proliferazione di Erlang in telecomunicazioni e adozione di Haskell nella progettazione aerospaziale e hardware .

Joel Spolsky ha scritto un post sul blog molto interessante, The Perils of JavaSchools , dove discute contro la (allora) tendenza delle università per favorire Java rispetto ad altre lingue, forse più difficili da imparare. Sebbene il post sul blog abbia poco a che fare con la programmazione funzionale, identifica un problema chiave:

Qui sta il dibattito. Anni di lamentele da parte di studenti pigri della CS come me, combinati con le lamentele dell'industria su come pochi laureati in CS si stanno laureando dalle università americane, hanno preso un tributo e nell'ultimo decennio un gran numero di scuole altrimenti perfettamente buone sono diventate Java al 100%. È alla moda, i reclutatori che usano "grep" per valutare i curriculum sembrano apprezzarlo e, soprattutto, non c'è nulla di abbastanza difficile in Java per eliminare davvero i programmatori senza la parte del cervello che fa puntatori o ricorsioni, quindi il i tassi di abbandono sono più bassi e i dipartimenti di informatica hanno più studenti e budget più grandi, e tutto va bene.

Ricordo ancora quanto odiavo Lisp, quando l'ho incontrata per la prima volta durante gli anni del college. È sicuramente un'amante severa, e non è una lingua in cui puoi essere immediatamente produttivo (beh, almeno non potrei). Rispetto a Lisp, Haskell (per esempio) è molto più amichevole, puoi essere produttivo senza troppi sforzi e senza sentirti un completo idiota, e questo potrebbe anche essere un fattore importante nel passaggio alla programmazione funzionale.

Tutto sommato, questa è una buona cosa. Numerosi linguaggi multiuso stanno adottando concetti di paradigma che prima potrebbero sembrare arcani alla maggior parte dei loro utenti e il divario tra i paradigmi principali si sta restringendo.

Domande correlate:

Ulteriori letture:


Grazie per la risposta (e molte idee interessanti). +1 Tuttavia, direi che introdurre (solo) lambda in un linguaggio di programmazione è un passo molto piccolo verso FP, e potrebbe anche essere fonte di confusione per molti (cosa stanno facendo i lambda da soli all'interno di un linguaggio imperativo?). Dopo aver appreso un po 'di Haskell, Scala e SML, non ho la sensazione di poter fare un vero FP con un linguaggio imperativo che supporta solo lambdas (che dire di curry e pattern matching, immutabilità?).
Giorgio,


2
@YannisRizos: Perl aveva funzioni anonime dalla prima versione di 5 (1994), ma non erano completamente "giusti" fino a 5.004 (1997).
Blrfl,

1
@penartur Questo è quello che ho pensato troppo, ma un editor amichevole mi ha rettificato da avermi qui: msdn.microsoft.com/en-us/library/0yw3tz5k%28v=vs.80%29.aspx
Yannis

Penso che forse il principale "evento" che ha portato alla popolarità dei linguaggi funzionali sia il web. Più specificamente, il passaggio dai programmi desktop al lato server. Ciò offre allo sviluppatore la libertà di scegliere qualsiasi linguaggio di programmazione. Paul Graham e Lisp negli anni '90 ne sono un esempio notevole.
Gilad Naor,

32

Penso che sia interessante quanto la popolarità della programmazione funzionale abbia parallelamente la crescita e la proliferazione di Javascript. Javascript ha molte caratteristiche radicali lungo lo spettro di programmazione funzionale che al momento della sua creazione (1995) non erano molto popolari tra i linguaggi di programmazione tradizionali (C ++ / Java). È stato iniettato improvvisamente nel mainstream come l'unico linguaggio di programmazione web sul lato client. Improvvisamente molti programmatori dovevano semplicemente conoscere Javascript e quindi dovevi conoscere qualcosa delle funzionalità del linguaggio di programmazione funzionale.

Mi chiedo quanto sarebbero popolari i linguaggi / caratteristiche funzionali se non fosse stato per l'improvvisa ascesa di Javascript.


5
Javascript è sicuramente un linguaggio importante, ma non sono sicuro che l'introduzione di Javascript possa spiegare da sola la popolarità della programmazione funzionale: negli ultimi anni sono comparsi molti altri linguaggi di programmazione funzionale, come ha illustrato Yannis nella sua risposta .
Giorgio,

8
@Giorgio - potrebbero esserci stati molti altri linguaggi di programmazione funzionale, ma (relativamente) nessuno li usa. L'uso di JS e la maggiore visione secondo cui il modo C ++ / Java di creare funzioni è doloroso e fastidioso sono in realtà le forze trainanti del mainstream, anche se i linguaggi più accademici confermano come dovrebbero essere implementati.
Telastyn,

1
La popolarità dei linguaggi dinamici in generale è suggerita come una spiegazione per la popolarità di Haskell: book.realworldhaskell.org/read/…
yannis,

Inoltre, il focus della domanda non è la popolarità di FP in generale, ma dell'introduzione tardiva di funzioni anonime in linguaggi generici e non funzionali. Anche se il grande pubblico (la maggior parte dei programmatori) non li conosceva, i progettisti del linguaggio li conoscevano molto bene. Ci deve essere stato un motivo per lasciarli fuori all'inizio. Forse sono stati considerati non intuitivi per gli sviluppatori dei primi anni '90.
Giorgio,

@giorgio - Sono molto più problematici da implementare rispetto a quelli in stile Java. Combinalo con la mancanza di conoscenza / adozione ed è una scelta di design abbastanza chiara.
Telastyn,

27

I gestori di eventi JavaScript e DOM hanno significato che milioni di programmatori dovevano imparare almeno un po 'sulle funzioni di prima classe per poter fare qualsiasi interattività sul web.

Da lì, è un passaggio relativamente breve per le funzioni anonime . Poiché JavaScript non si chiude this, ti incoraggia fortemente anche a conoscere le chiusure. E poi sei d'oro: capisci le funzioni anonime di prima classe che si chiudono al di sopra degli ambiti lessicali.

Una volta che ti senti a tuo agio, lo vuoi in ogni lingua che usi.


7
+1 non riguarda solo funzioni anonime. Le chiusure sono un concetto molto più ampio della semplice definizione di una funzione temporanea in linea.
Phkahler,

@phkahler: hai ragione e, in questo senso, Java ha già delle chiusure (e persino più potente di quello che ottieni con una funzione letterale) ma manca una notazione concisa per il caso comune di una classe anonima a un metodo.
Giorgio,

17

Non è certo l' unico fattore, ma sottolineerò la popolarità di Ruby. Non dire questo è più importante di una qualsiasi delle sei risposte già alla lavagna, ma penso che siano successe molte cose contemporaneamente e che sia utile elencarle tutte.

Ruby non è un linguaggio funzionale e i suoi lambda, pungoli e blocchi sembrano goffi quando hai usato qualcosa come ML, ma il fatto è che ha reso popolare l'idea di mappatura e riduzione a una generazione di giovani programmatori che fuggono da Java e PHP per hipper pascoli. Le lambda in diverse lingue sembrano essere mosse difensive più di ogni altra cosa ("Restate in giro! Abbiamo anche quelle !!)

Ma la sintassi del blocco e il modo in cui si sono integrati con .each, .map, .reduce e così via hanno reso popolare l'idea di una funzione anonima anche se è davvero un costrutto sintattico che si comporta come una coroutine. E la facile conversione in un proc via e lo rende un farmaco gateway per la programmazione funzionale.

Sostengo che i programmatori di Ruby on Rails che scrivono JavaScript erano già pronti a fare le cose in uno stile funzionale leggero. Abbinalo al blogging programmatore, all'invenzione di Reddit, hacker News e Stack Overflow nello stesso momento e le idee si diffondono più velocemente su Internet rispetto ai giorni dei Newsgroup.

TL; DR: Ruby, Rails, JavaScript, blogging e Reddit / Hacker News / Stack Overflow hanno spinto le idee funzionali su un mercato di massa, quindi tutti le volevano nelle lingue esistenti per prevenire ulteriori defezioni.


2
+1 Per una buona risposta e (se potessi, perché ho solo un voto) +1 per aver sottolineato che "I lambda in diverse lingue sembrano essere mosse difensive più di ogni altra cosa (" Restate in giro! Abbiamo anche quelle !!) ". Penso che anche questo sia un fattore. Per alcune lingue le lambda sono una caratteristica piacevole che, sebbene aggiunga pochissimo potere espressivo alla lingua nel suo insieme, dà alla lingua un po 'di popolarità (un il numero di programmatori sembra pensare che il supporto per le funzioni anonime equivale a supportare pienamente la programmazione funzionale.
Giorgio

2
Penso davvero che questo sia il motivo per cui la maggior parte delle lingue ha implementato la sintassi a blocchi negli ultimi anni. Ma l'unico modo per essere sicuri è chiedere agli sviluppatori linguistici quali fossero i loro motivi. Possiamo solo speculare su imo.
SpoBo,

per me, Ruby è il linguaggio che per primo ha reso i blocchi rock e molto accattivanti, quindi +1. Anche Haskell avrebbe potuto avere un effetto.
rogerdpack,

13

Come ha sottolineato Yannis , ci sono una serie di fattori che hanno influenzato l'adozione di funzioni di alto livello in lingue che prima erano prive. Uno degli elementi importanti su cui ha solo leggermente accennato è la proliferazione di processori multi-core e, con ciò, il desiderio di un'elaborazione più parallela e simultanea.

La mappa / filtro / riduzione dello stile di programmazione funzionale è molto amichevole alla parallelizzazione, consentendo al programmatore di utilizzare facilmente più core, senza scrivere alcun codice di threading esplicito.

Come osserva Giorgio, la programmazione funzionale offre molto di più che funzioni di alto livello. Le funzioni, oltre a una mappa / filtro / riduzione del modello di programmazione e l' immutabilità sono il nucleo della programmazione funzionale. Insieme, queste cose costituiscono potenti strumenti di programmazione parallela e concorrente. Per fortuna, molte lingue supportano già alcune nozioni di immutabilità e, anche se non lo fanno, i programmatori possono considerare le cose come immutabili, consentendo alle librerie e al compilatore di creare e gestire operazioni asincrone o parallele.

L'aggiunta di funzioni di alto livello a una lingua è un passaggio importante per semplificare la programmazione concorrente.

Aggiornare

Aggiungerò un paio di esempi più dettagliati per rispondere alle preoccupazioni che Loki ha notato.

Considera il seguente codice C # che attraversa una raccolta di widget, creando un nuovo elenco di prezzi dei widget.

List<float> widgetPrices;
    float salesTax = RetrieveLocalSalesTax();
foreach( Widget w in widgets ) {
    widgetPrices.Add( CalculateWidgetPrice( w, salesTax ) );
}

Per una vasta raccolta di widget o un metodo CalculateWidgetPrice (Widget) ad alta intensità computazionale, questo ciclo non farebbe buon uso di tutti i core disponibili. Per eseguire i calcoli dei prezzi su diversi core, il programmatore dovrebbe creare e gestire esplicitamente thread, passando il lavoro e raccogliendo i risultati insieme.

Prendi in considerazione una soluzione una volta aggiunte le funzioni di ordine superiore a C #:

var widgetPrices = widgets.Select( w=> CalculateWidgetPrice( w, salesTax ) );

Il ciclo foreach è stato spostato nel metodo Select, nascondendone i dettagli di implementazione. Tutto ciò che rimane al programmatore è dire Seleziona quale funzione applicare a ciascun elemento. Ciò consentirebbe all'implementazione Select di eseguire i calcoli in parallelo, gestendo tutti i problemi di sincronizzazione e gestione dei thread senza il coinvolgimento del programmatore.

Ma, ovviamente, Select non fa il suo lavoro in parallelo. È qui che entra in gioco l'immutabilità. L'implementazione di Select non sa che la funzione fornita (CalculateWidgets sopra) non ha effetti collaterali. La funzione potrebbe cambiare lo stato del programma al di fuori della vista di Select e della sua sincronizzazione, rompendo tutto. Ad esempio, in questo caso il valore di salesTax potrebbe essere modificato per errore. I linguaggi funzionali puri forniscono immutabilità, quindi la funzione Seleziona (mappa) può sapere con certezza che nessuno stato sta cambiando.

C # risolve questo problema fornendo PLINQ in alternativa a Linq. Sembrerebbe che:

var widgetPrices = widgets.AsParallel().Select(w => CalculateWidgetPrice( w, salesTax) );

Il che fa pieno uso di tutti i core del tuo sistema senza una gestione esplicita di quei core.


Indico il desiderio di un'elaborazione più parallela e simultanea, è discusso nell'articolo ACM "Una storia di Erlang" a cui sto collegando nel quarto paragrafo. Ma è un ottimo punto e probabilmente avrei dovuto approfondire un po 'di più. +1 perché ora non devo; P
yannis

Hai ragione, non ho guardato abbastanza attentamente. Ho modificato la mia osservazione.
Ben

Oh, non
dovevi

4
Nessuno di ciò che descrivi sopra richiede lambda. La stessa funzionalità si ottiene altrettanto facilmente con le funzioni con nome. Qui stai semplicemente documentando a causee a perceived affectsenza spiegare il correlation. L'ultima riga dell'IMO riguarda la questione; ma non hai risposto. Perché semplifica la programmazione concorrente.
Martin York,

@Ben: fai attenzione che il tuo esempio riguardi funzioni di ordine superiore che non richiedono funzioni anonime per essere utilizzate. La tua risposta contiene idee interessanti (per un'altra domanda) ma sta andando fuori tema in questo momento.
Giorgio,

9

Sono d'accordo con molte delle risposte qui, ma la cosa interessante è che quando ho saputo delle lambda e ci sono saltato sopra, non è stato per nessuno dei motivi che altri hanno menzionato.

In molti casi, le funzioni lambda semplicemente migliorano la leggibilità del codice. Prima di lambdas quando chiamavi un metodo che accettava un puntatore a funzione (o funzione, o delegato), dovevi definire il corpo di quella funzione da qualche altra parte, quindi quando avevi un costrutto "foreach", il tuo lettore avrebbe dovuto passare a un altro parte del codice per vedere esattamente cosa stavi pianificando di fare con ogni elemento.

Se il corpo della funzione che elabora gli elementi è solo poche righe, utilizzerei una funzione anonima perché ora quando leggi il codice, la funzionalità rimane invariata, ma il lettore non deve saltare avanti e indietro, l'intera implementazione è proprio lì di fronte a lui.

Molte delle tecniche di programmazione funzionale e parallelizzazione potrebbero essere realizzate senza funzioni anonime; dichiarane uno normale e passa un riferimento a quello ogni volta che è necessario. Ma con lambda la facilità di scrittura del codice e la facilità di lettura del codice sono notevolmente migliorate.


1
Ottima spiegazione (+1). I programmatori di Lisp sono consapevoli di tutto ciò dal 1958. ;-)
Giorgio,

4
@Giorgio: Certo, ma i programmatori lisp dovevano anche acquistare tastiere speciali con i tasti di parentesi aperta / chiusa rinforzati :)
DXM,

@DXM: non le tastiere, ottengono un dispositivo di input aggiuntivo che è un po 'come i pedali del piano per l'apertura e la chiusura della parentesi ;-)
vartec

@DXM, vartec: ultimamente ho fatto un po 'di Schema e trovo che le parentesi siano OK. Alcuni codici C ++ possono essere molto più criptici (e ho molta più esperienza con C ++ che con Scheme). :-)
Giorgio

9

Essendo stato coinvolto un po 'nella storia recente qui, credo che un fattore sia stato l'aggiunta di generici a Java e .NET. Ciò porta naturalmente a Func < , > e ad altre astrazioni computazionali fortemente tipizzate (Task < >, Async < > ecc.)

Nel mondo .NET abbiamo aggiunto queste funzionalità proprio per supportare FP. Ciò ha innescato una serie a cascata di lavoro linguistico relativo alla programmazione funzionale, in particolare C # 3.0, LINQ, Rx e F #. Quella progressione ha influenzato anche altri ecosistemi e continua ancora oggi in C #, F # e TypeScript.

Aiuta anche Haskell a lavorare in MSR, ovviamente :)

Naturalmente c'erano anche molte altre influenze (certamente JS) e questi passaggi erano a loro volta influenzati da molte altre cose - ma l'aggiunta di generici a questi linguaggi aiutò a rompere la rigida ortodossia OO della fine degli anni '90 in gran parte del mondo del software e aiutò ad aprire la porta per FP.

Don Syme

ps F # era il 2003, non il 2005, sebbene diremmo che non ha raggiunto la 1.0 fino al 2005. Abbiamo anche realizzato un prototipo Haskell.NET nel 2001-02.


Benvenuto! Ho usato il 2005 per F #, dato che è l'anno riportato nell'articolo Wikipedia di F # come l'anno della prima versione stabile. Vorresti che lo cambiassi nel 2003?
yannis,


4

Da quello che vedo, la maggior parte delle risposte si concentra sulla spiegazione del perché la programmazione funzionale in generale è tornata ed è entrata nel mainstream. Ho pensato che questo non rispondesse davvero alla domanda sulle funzioni anonime in particolare e sul perché improvvisamente diventarono così popolari.

Ciò che ha davvero guadagnato la popolarità, sono le chiusure . Poiché nella maggior parte dei casi le chiusure sono funzioni a eliminazione diretta passate variabili, ha ovviamente senso utilizzare una sintassi delle funzioni anonima per queste. E infatti in alcune lingue è l'unico modo per creare la chiusura.

Perché le chiusure hanno guadagnato popolarità? Perché sono utili nella programmazione guidata dagli eventi, durante la creazione di funzioni di callback . Attualmente è il modo di scrivere il codice client JavaScript (in realtà è il modo di scrivere qualsiasi codice GUI). Attualmente è anche il modo di scrivere codice back-end altamente efficiente e codice di sistema, poiché il codice scritto nel paradigma basato sugli eventi è generalmente asincrono e non bloccante . Per il back-end questo è diventato popolare come soluzione al problema C10K .


Grazie per aver sottolineato che questa domanda non riguarda la programmazione funzionale (+1) perché (1) l'idea di un blocco di codice che viene passato come argomento viene utilizzata anche in linguaggi non funzionali come Smalltalk e (2) stato mutante catturato dal contesto lessicale di una chiusura (il più possibile in molte implementazioni lambda) è decisamente non funzionale . E sì, avendo chiusure, il passaggio alle chiusure anonime è breve. La cosa interessante è che le chiusure sono note da molto tempo e la programmazione guidata dagli eventi è stata utilizzata (per quanto ne so) dagli anni Ottanta.
Giorgio,

Ma forse è stato solo negli ultimi anni che è diventato chiaro che le chiusure possono essere utilizzate molto più spesso di quanto si pensasse in precedenza.
Giorgio,

@Giorgio: sì, la maggior parte dei concetti attualmente in uso sono in circolazione da molto, molto tempo. Eppure non sono stati usati nel modo in cui sono usati adesso.
vartec,

1

Penso che il motivo sia la crescente prevalenza della programmazione concorrente e distribuita, in cui il nucleo della programmazione orientata agli oggetti (incapsulando lo stato mutevole con gli oggetti) non si applica più. Nel caso di un sistema distribuito, perché non v'è alcun stato condiviso (e software astrazioni di tale nozione perde) e nel caso di un sistema concorrente, perché correttamente sincronizzazione accesso allo stato condiviso è stato dimostrato ingombrante e soggetto ad errori. Cioè, uno dei principali vantaggi della programmazione orientata agli oggetti non si applica più a molti programmi, rendendo il paradigma orientato agli oggetti molto meno utile di prima.

Al contrario, il paradigma funzionale non utilizza lo stato mutabile. Qualsiasi esperienza acquisita con paradigmi e schemi funzionali è quindi più immediatamente trasferibile al calcolo simultaneo e distribuito. E piuttosto che reinventare la ruota, l'industria ora prende in prestito quegli schemi e le caratteristiche del linguaggio per rispondere alle sue necessità.


4
Le funzioni anonime in alcune lingue del flusso principale (ad es. C ++ 11) consentono lo stato mutabile (possono persino acquisire variabili dall'ambiente di definizione e modificarle durante la loro esecuzione). Quindi penso che parlare del paradigma funzionale in generale e dell'immutabilità in particolare sia un po 'fuori dalla portata della domanda che viene posta.
Giorgio,

Dopo aver appena letto alcune note sulle funzionalità di Java 8, uno degli obiettivi principali del progetto lambda è supportare la concorrenza. E QUELLO ci porta immediatamente alla bomba a grappolo della mutabilità in cui si imbatteranno tutti questi meravigliosi javabeani. Una volta che Java ottiene lambdas (supponendo che lo faccia davvero nella versione finale della versione 8), hanno quindi bisogno di affrontare il problema immutabile per impostazione predefinita, in qualche modo (distrugge il linguaggio, pensando in Lisp - funzioni senza effetti collaterali - invece di in COBOL - colpisci su DATA DIVISION / COPYBOOK)
Roboprog

Ben detto. L'allontanamento dallo stato mutevole rende la concorrenza più semplice e le tecnologie come cascalog e spark distribuiscono facilmente la programmazione funzionale su un cluster di computer. Vedi glennengstrand.info/analytics/distributed/functional/… per maggiori dettagli su come e perché.
Glenn,

1

Se potessi aggiungere i miei 0,02 €, anche se sarei d'accordo con l'importanza dell'introduzione di JavaScript nel concetto, penso che più della programmazione concorrente darei la colpa alla moda attuale della programmazione asincrona. Quando si effettuano chiamate asincrone (necessarie con le pagine Web), le funzioni anonime semplici sono così ovviamente utili, che ogni programmatore web (cioè ogni programmatore) ha dovuto acquisire familiarità con il concetto.


1

Un altro esempio molto antico di qualcosa di simile a funzioni anonime / lambdas è la chiamata per nome in Algol 60. Si noti tuttavia che la chiamata per nome è più vicina al passaggio di macro come parametri che al passaggio di funzioni vere, ed è più fragile / difficile da capire di conseguenza.


0

Qui la discendenza al meglio delle mie conoscenze.

  • 2005: Javascript ha di recente portato la programmazione di ordine superiore con lambdas di nuovo nel mainstream. In particolare librerie come underscore.js e jquery . Una delle prime di queste librerie era prototype.js che precede jquery di circa un anno. Prototype si basa sul modulo Enumerable di Ruby, che ci porta a ...
  • 1996: il modulo Enumerable di Ruby ovviamente prende ispirazione dal framework di raccolta di Smalltalk. Come è stato menzionato da Matz in molte interviste, che ci porta a ...
  • 1980: Smalltalk utilizza molta programmazione di ordine superiore e fornisce un'API di raccolta che fa un uso intensivo della programmazione di ordine superiore (ad esempio, la classe Iterable di GNU Smalltalk ). Nel codice idiomatico Smalltalk non troverai alcun loop ma solo enumerazioni di alto ordine. Sfortunatamente quando Java, quando il framework di raccolta di Smalltalk fu portato su Java nel 1998, le enumerazioni di ordine superiore furono lasciate fuori. Ecco come la programmazione di ordine superiore è stata gradualmente eliminata dal mainstream per i prossimi dieci anni a venire! Smalltalk ha molti antenati, ma rilevante per la domanda di OP è LISP, che ci porta a ...
  • 1958: LISP, ovviamente, ha al centro la programmazione di ordine superiore.

Amiss, ovviamente, è l'intera discendenza ML. ML, SML, OCaml, Haskell, F #. Che deve contare per qualcosa ..
Muhammad Alkarouri,

-1

Le funzioni anonime sono utili perché nominare le cose è difficile e se si utilizza una funzione solo una volta, non è necessario un nome.

Le funzioni Lambda sono diventate mainstream solo di recente perché fino a poco tempo fa, la maggior parte delle lingue non supportava le chiusure.

Vorrei suggerire che Javascript ha spinto questo mainstream. È un linguaggio universale che non ha modo di esprimere il parallelismo e le funzioni anonime facilitano l'uso dei modelli di callback. Inoltre hanno contribuito lingue popolari come Ruby e Haskell.


1
"Le funzioni Lambda sono diventate mainstream solo di recente perché fino a poco tempo fa, la maggior parte delle lingue non supportava le chiusure.": Questo ragionamento suona un po 'circolare per me: essere mainstream significa che la maggior parte delle lingue lo supporta. Si potrebbe immediatamente chiedere "Cosa ha scatenato la popolarità delle chiusure nei moderni linguaggi di programmazione".
Giorgio,

So che Python non ha la migliore implementazione di lambdas. Ma in termini di popolarità, probabilmente ha contribuito più di Haskell.
Muhammad Alkarouri,
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.