perché nessun compilatore nativo di C # o altro linguaggio "produttivo"? [chiuso]

5

Ho letto di D and Go e il modo in cui mirano a essere compilati per codice macchina, ma sono convenienti (come la garbage collection, non c'è bisogno di manipolare i puntatori se non necessario) e sono d'accordo che c'è bisogno di un tale linguaggio . Tuttavia i progettisti di entrambi i Go e D per qualche ragione hanno deciso di inventare una nuova lingua. Perché? Perché non prendere il linguaggio esistente che è popolare, dimostrato di essere produttivo ma non è compilato in codice nativo come C #? Quali sono le ragioni tecnologiche per questo? Sarebbe difficile implementare la garbage collection (D fa), linq o qualcosa del tutto altrimenti?

    
posta ren 23.12.2013 - 00:04
fonte

5 risposte

6

Nel caso di Java, è perché volevano che fosse eseguito su molte architetture diverse (ricorda che le sue radici erano per un sistema embedded). In base a ciò, hanno pensato che sarebbe stato meglio fornire un livello intermedio (la VM) in modo che il codice java potesse essere scritto per il livello, quindi non sarebbe necessario fornire implementazioni diverse per ciascuna piattaforma. Invece il layer verrebbe costruito per ogni piattaforma.

Quando Microsoft ha iniziato a creare .NET, la sua era così strongmente progettata per essere Java (in effetti utilizzava gran parte del vecchio codice J ++ che avevano già, e il capo progettista era il tipo che ha lavorato alla loro implementazione Java) quindi comprensibile hanno mantenuto il più piccolo possibile al fine di produrre qualcosa di più veloce. Penso che abbiano anche ipotizzato che avrebbero potuto fare più ottimizzazioni nel JIT in fase di runtime, quindi non sarebbe stato molto più lento.

Perché non hanno un compilatore nativo per ora è discutibile. Probabilmente hanno deciso che non è necessario, il codice .NET ha semplicemente la VM installata insieme alla libreria di runtime, quindi far sì che generi codice "puro" nativo sarebbe una perdita di tempo per loro.

Confronta questo con Mono che però genera codice nativo.

Penso che i ragazzi che hanno creato D and Go non volessero limitarsi a usare la tecnologia Microsoft (comprensibile), e forse solo perché a loro piace creare un nuovo linguaggio (ci sono già abbastanza lingue, ne sono appena 2 nuove! !).

    
risposta data 23.12.2013 - 00:31
fonte
6

In tutte le normali implementazioni di C # e Java, almeno una parte del codice è eventualmente compilata nel codice nativo.

Le implementazioni Java più utilizzate sono Oracle JDK / OpenJDK, che consiste in un compilatore in anticipo che compila codice byte Java in JVM e una VM in modalità mista, che inizia a interpretare il codice byte JVM e le compattazioni JIT le parti sensibili al rendimento nel codice macchina nativo.

In .NET, nessun codice viene mai interpretato, tutto il codice viene compilato nel codice macchina nativo prima che venga eseguito.

    
risposta data 23.12.2013 - 03:28
fonte
3

Si presume che il processo di pensiero dietro a Go e D fosse "vogliamo un linguaggio compilato su un codice nativo che non sia C o C ++". Quindi ti chiedi perché i progettisti non hanno solo scritto compilatori di codice nativo per Java o C #.

Ma chi dice che questo era il processo mentale dietro quelle lingue? Non posso parlare per i designer, ovviamente, ma da quello che ho letto, l'idea principale di D era "C ++ ha una sintassi che rende i compilatori complicati e lenti, e la metaprogrammazione usando i template è un incubo illeggibile, posso fare un linguaggio che può fare metaprogrammazione meglio di C ++ ". Tieni presente che il progettista principale di D è uno scrittore di compilatori C ++.

Inoltre, non è così semplice compilare Java e C # in codice nativo. Il bytecode di Java fa parte dell'interfaccia documentata dell'ambiente di runtime Java. È assolutamente legale per un programma Java generare bytecode in fase di esecuzione e quindi utilizzare un programma di caricamento classi per caricarlo. Lo stesso vale per C #. In effetti, le librerie di espressioni regolari e altre cose spesso fanno esattamente questo. Hai librerie di derisione, librerie di aspetto, tutte queste cose amano confondere con bytecode. Se provi a creare un ambiente nativo per Java o C #, queste cose smettono di funzionare. Quindi nel migliore dei casi è possibile compilare un sottoinsieme di Java nel codice nativo. Ma poi affronti il fatto che tutto ciò che viene fatto in fase di esecuzione è in realtà una parte importante del modo in cui questi linguaggi vengono utilizzati; sostituisce le cose che vengono fatte con la generazione di codice offline o trucchi di compilazione in altre lingue.

    
risposta data 19.03.2014 - 18:05
fonte
2

I modelli in C ++ rendono possibile che un file sorgente relativamente piccolo generi un numero arbitrario di funzioni diverse, ognuna contenente una sequenza diversa di istruzioni, ma affinché un programma sia effettivamente eseguito, il numero di tali funzioni deve essere limitato .

I generici in linguaggi .NET come C # consentono anche a un piccolo file sorgente di specificare un numero enorme di funzioni, ma non è necessario generare effettivamente le istruzioni per nessuno di essi fino a quando non vengono effettivamente eseguiti. Mentre C ++ si strozzerà se un modello genererebbe un numero infinito di funzioni, C # non avrà problemi, data la possibilità di posticipare la generazione del codice macchina fino al runtime .

Mentre sarebbe possibile avere un compilatore che generi codice nativo che includa al suo interno un meccanismo per generare ulteriore codice su richiesta, un generatore di codice che produce codice ottimizzato sarà una bestia piuttosto complicata. È più semplice avere il codice di rendering del compilatore in un modulo in cui i generici non devono essere estesi nelle istruzioni della macchina e quindi avere un JITter ("compilatore Just In Time") che può prendere il codice di quel modulo, insieme a un elenco di richieste sostituzioni di tipo e producono una rappresentazione in codice macchina di un metodo che funziona con i tipi necessari.

    
risposta data 19.03.2014 - 16:40
fonte
1

Per espandere l'osservazione di Jorg -

link

Se si osserva la vasta gamma di variazioni delle architetture della CPU su cui gira .NET, si può vedere un certo valore nella conversione al codice macchina nell'ultimo istante possibile. Guardando le permutazioni di Pentium, Atomi, Xeoni, Opteron, ecc. Si trovano vari sottoinsiemi di istruzioni presenti o assenti, variazioni nei bus front side, co-processori grafici, ecc. È una buona idea per gli sviluppatori che scrivono CRUD di spendere anche un ripensandoci su questa roba?

    
risposta data 23.12.2013 - 08:52
fonte

Leggi altre domande sui tag