La risposta breve è: non lo sappiamo , chiediamo di nuovo tra 100 anni. (Potremmo ancora non saperlo allora; forse non lo sapremo mai.)
In teoria, questo è possibile. Prendi tutti i programmi che sono mai stati scritti, traducili manualmente nel codice macchina più efficiente possibile e scrivi un interprete che associ i codici sorgente ai codici macchina. Ciò è possibile poiché è stato scritto solo un numero limitato di programmi (e man mano che vengono scritti più programmi, mantenere le traduzioni manuali). Anche questo è ovviamente completamente idiota in termini pratici.
Inoltre, in teoria, linguaggi di alto livello potrebbero essere in grado di raggiungere le prestazioni del codice macchina, ma non lo supereranno. Questo è ancora molto teorico, perché in termini pratici, molto raramente ricorriamo alla scrittura di codice macchina. Questo argomento non si applica al confronto tra linguaggi di livello superiore: non implica che C debba essere più efficiente di Python, solo che il codice macchina non può fare peggio di Python.
Venendo dall'altra parte, in termini puramente sperimentali, possiamo vedere che la maggior parte delle volte , le lingue di alto livello interpretate hanno prestazioni peggiori rispetto alle lingue di basso livello compilate. Tendiamo a scrivere codice non sensibile al tempo in linguaggi di altissimo livello e loop interni critici nel tempo, con linguaggi come C e Python in mezzo. Anche se non ho statistiche a sostegno di questo, penso che questa sia davvero la decisione migliore nella maggior parte dei casi.
Tuttavia, ci sono casi non contestati in cui linguaggi di alto livello battono il codice che si potrebbe realisticamente scrivere: ambienti di programmazione per scopi speciali. Programmi come Matlab e Mathematica sono spesso molto più bravi a risolvere alcuni tipi di problemi matematici rispetto a ciò che i semplici mortali possono scrivere. Le funzioni della biblioteca potrebbero essere state scritte in C o C ++ (che è il carburante verso il campo "le lingue di basso livello sono più efficienti"), ma non è affar mio se sto scrivendo il codice Mathematica, la biblioteca è una scatola nera.
È teoricamente possibile che Python si avvicini, o forse sia ancora più vicino, a prestazioni ottimali rispetto a C? Come visto sopra, sì, ma oggi siamo molto lontani da quello. Ancora una volta, i compilatori hanno fatto molti progressi negli ultimi decenni e questi progressi non stanno rallentando.
Le lingue di alto livello tendono a rendere più automatiche le cose, quindi hanno più lavoro da svolgere e quindi tendono ad essere meno efficienti. D'altra parte, tendono ad avere più informazioni semantiche, quindi può essere più facile individuare ottimizzazioni (se stai scrivendo un compilatore Haskell, non devi preoccuparti che un altro thread modificherà una variabile sotto il tuo naso). Uno dei numerosi sforzi per confrontare i diversi linguaggi di programmazione di mele e arance è il Computer Language Benchmark Game (precedentemente noto come shootout). Fortran tende a brillare in compiti numerici; ma quando si tratta di manipolare dati strutturati o commutazione di thread ad alta velocità, F # e Scala fanno bene. Non prendere questi risultati come vangelo: molto di ciò che stanno misurando è quanto è stato bravo l'autore del programma di test in ogni lingua.
Un argomento a favore di linguaggi di alto livello è che le prestazioni sui sistemi moderni non sono così fortemente correlate al numero di istruzioni eseguite, e meno nel tempo. Le lingue di basso livello sono buone corrispondenze per semplici macchine sequenziali. Se un linguaggio di alto livello esegue il doppio delle istruzioni, ma riesce a utilizzare la cache in modo più intelligente, quindi fa la metà del numero di errori nella cache, potrebbe finire per vincere.
Sulle piattaforme server e desktop, le CPU hanno quasi raggiunto un plateau dove non ottengono più velocemente (anche le piattaforme mobili ci stanno arrivando); ciò favorisce le lingue in cui il parallelismo è facile da sfruttare. Molti processori trascorrono la maggior parte del loro tempo in attesa di una risposta I / O; il tempo impiegato nel calcolo conta poco rispetto alla quantità di I / O e un linguaggio che consente al programmatore di ridurre al minimo le comunicazioni è un vantaggio.
Tutto sommato, mentre le lingue di alto livello iniziano con una penalità, hanno più margini di miglioramento. Quanto possono avvicinarsi? Chiedi di nuovo tra 100 anni.
Nota finale: spesso il confronto non è tra il programma più efficiente che può essere scritto nella lingua A e lo stesso nella lingua B, né tra il programma più efficiente mai scritto in ciascuna lingua, ma tra il programma più efficiente che può essere scritto da un essere umano in un certo periodo di tempo in ogni lingua. Ciò introduce un elemento che non può essere analizzato matematicamente, neppure in linea di principio. In termini pratici, ciò spesso significa che la migliore prestazione è un compromesso tra quanto codice di basso livello devi scrivere per raggiungere gli obiettivi di prestazione e quanto codice di basso livello hai tempo per scrivere per rispettare le date di rilascio.