Managed Coders vs Native Coder


19

Sono un programmatore e ho esperienza con codice sia nativo che gestito. Ho iniziato con Pascal e C, poi mi sono trasferito in C ++ e infine in C #.

Nel corso dell'ultimo anno o giù di lì, ho programmato quasi esclusivamente in C # e ho perso molto di ciò che era naturale quando ero un programmatore C ++.

Qualche settimana fa, quando mi sono seduto per scrivere un codice C ++ nativo, mi sono ritrovato a armeggiare mentre lentamente mi facevo conoscere le complessità, le stranezze e le idiosincrasie di tutto ciò. Sono quasi imbarazzato nel dire che avevo completamente dimenticato che passare una matrice allocata in modo dinamico a una funzione senza passare anche la sua dimensione significherebbe che la funzione di ricezione non avrebbe modo di sapere quanto è lunga la matrice.

Esistono innumerevoli articoli e documenti che confrontano e contrastano il codice gestito rispetto a quello non gestito. Sappiamo tutti che il codice nativo, se ben ottimizzato, può essere eseguito in modo significativamente più veloce e leggero del codice gestito. D'altra parte, il codice gestito ha garbage collector e l'ottimizzazione specifica della CPU e del sistema operativo in fase di runtime che può far funzionare il codice nativo per i suoi soldi.

Puramente dal punto di vista tecnico, non esiste un chiaro vincitore.

Non c'è dubbio che il codice gestito è più semplice da codificare e comprendere per ordini di grandezza. Basta guardare la differenza nel numero di righe necessarie per costruire una semplice GUI in Win32 C ++ vs C #.

Ai miei tempi con i codici nativi, scrivevo principalmente simulazioni matematiche su supercomputer. Avevano brutti CLI ed erano principalmente focalizzati sugli algoritmi. Oggi scrivo in C # e produco bellissime applicazioni GUI, ma mi perderei se dovessi creare qualcosa di simile calibro su una lingua madre. Anche con un framework come QT, ci vorrebbe ancora il doppio del tempo per produrre qualcosa in C ++ / QT rispetto a quanto farebbe in C #.

Ogni volta che vedo qualcuno che ha scritto un'applicazione GUI su larga scala e completa in C / C ++, non posso fare a meno di provare un senso di timore reverenziale e un pizzico di gelosia.

Sono curioso di sapere come altri programmatori esperti vedono le lingue gestite e non gestite. Vedi il codice gestito come amatoriale ? Vedi i programmatori nativi come più hardcore ?

java  .net 

Risposte:


26

Il mio lavoro quotidiano è attualmente in C ++, ma ho programmato in diverse lingue abbastanza a lungo da non notare quasi più alcuna differenza. Ecco le mie osservazioni:

  • Molte delle presunte inefficienze con altri linguaggi sono spesso reimplementate dai programmatori C ++ come best practice. Aggiungiamo un numero sufficiente di controlli null, controllo dei limiti dell'array, controllo del tipo, convalida dell'input, ecc. Per negare in gran parte qualsiasi vantaggio di velocità di esecuzione ottenuto dalla lingua che non esegue automaticamente queste operazioni, almeno per il codice che non richiede un'elaborazione intensiva dei dati.
  • Quella piastra aggiuntiva diventa un'abitudine radicata dopo un po ', in modo che non sembri davvero un lavoro extra e sporge come un pollice dolente quando manca.
  • Quando programmo in una lingua "gestita" penso ancora all'allocazione della memoria, in modo da assicurarmi di non creare una perdita di memoria. Forse non deletesto esprimendo esplicitamente , ma sono ancora consapevole nella mia mente del punto in cui il garbage collector lo considera idoneo per la cancellazione. Ho avuto più difficoltà a risolvere problemi di memoria insufficiente a partire da Java rispetto a quanto avessi mai fatto in C ++, probabilmente perché in C ++ sono molto più difficili da ignorare per molto tempo.
  • Lo stesso vale per la digitazione dinamica. Devo ancora tenere traccia nella mia testa se un parametro di funzione è un array, un int o una stringa. In realtà, richiede più sforzo mentale perché il tipo non è chiaramente elencato proprio lì per me.
  • Lo stile C ++ moderno è molto diverso dall'era pre-C #. Piuttosto che cambiare la lingua, le persone "hanno scoperto" come utilizzare le funzionalità C ++ esistenti in modi unici per evitare gran parte della gestione della memoria del passato. I modelli di progettazione che liberano memoria automaticamente sono molto comuni ora.
  • Per quanto ne so, anche se è possibile creare applicazioni GUI solo scrivendo codice, i progettisti grafici come QT designer sono il metodo ampiamente preferito, con il codice utilizzato principalmente solo per i gestori di eventi o la personalizzazione del runtime.
  • Le lingue che non hai usato ampiamente per un po 'sembrano sempre un po' goffe, anche se ricordi principalmente la sintassi. Se non scrivo Python per un anno, ci sono molte idiosincrasie che ho dimenticato, e sembra più imbarazzante del C ++ per un po ', anche se oggettivamente la maggior parte delle persone considera Python il linguaggio "più semplice".

Con la combinazione di tutti questi fattori, il mio modello mentale rimane abbastanza coerente tra quando programma in C ++ e altre lingue, e le differenze sembrano per lo più semplicemente sintattiche. Certo, gran parte di ciò è il risultato di formazione, abitudine, standard di codifica e modelli di progettazione moderni piuttosto che caratteristiche intrinseche al linguaggio C ++ stesso, ma il confronto è ancora valido.

Immagino che ciò che sto cercando di dire sia che nella mia esperienza l'addestramento del programmatore fa molta più differenza rispetto alla lingua che sta usando.


20

Vedi il codice gestito come amatoriale? Vedi i programmatori nativi come più hardcore?

No.

Vedo le differenze tra un ingegnere e un programmatore. L' ingegnere hardcore sceglierà sempre lo stack di lingua / tecnologia appropriato per eseguire il lavoro nel minor tempo possibile a uno standard di runtime accettabile.

Con la potenza del processore in questi giorni, la frequenza di dover effettivamente ottenere il massimo da una macchina utilizzando un livello inferiore, le lingue native stanno diventando sempre meno. Di solito non c'è davvero un caso aziendale per questo. La produttività supererà sempre una differenza di alcuni millisecondi nel tempo di esecuzione.


+1, ma tieni presente che questo è un effetto economico - se un ciclo di calcolo costa $ 1 milione, allora l'ottimizzazione estrema regnerebbe - o non ci preoccuperemmo affatto dei computer ...
Gary Rowe,

10
a parte il fatto che vediamo prestazioni complessivamente inferiori: Word6 funziona come l'illuminazione su hardware moderno, Word2010 impiega un minuto solo per caricarsi. Oggi abbiamo bisogno di quell'hardware superveloce per stare al passo con i programmatori!
gbjbaanb,

2
@gbjbaanb: qualunque sia la scelta dei programmatori, qualsiasi base di codice sufficientemente grande sarà lenta. IIRC, Word è ancora scritto in C ++ (e sarei disposto a scommettere che una parte significativa di tutto il codice Word 6 legacy è ancora lì).
Steven Evers,

2
@gbjbaanb, Word 2010 non è una riscrittura diretta di Word 6 in .NET. Aggiunge molte più funzionalità e deve gestire molti più scenari di utilizzo. È un'applicazione molto, molto più grande di Word 6.
Mircea Chirea,

6

Purtroppo, Microsoft ci ha portato a confondere "Managed Code" con le librerie di classe C # /. Net.

Ci sono due cose separate e quasi non correlate in gioco qui.

  1. Belle librerie .Net.

  2. Codice gestito.

C # offre entrambi in un pacchetto ordinato, supportato e facile da usare a un prezzo.

C ++ ha numerose librerie interessanti che fanno quasi tutto ciò che fa .Net. Invece di incolpare il codice "nativo C ++" come avere più "complessità, stranezze e idiosincrasie" rispetto al codice C # /. Net, potresti cercare migliori librerie C ++.

Biblioteche migliori consentono anche di scrivere un bel codice C ++.

Ogni volta che vedo qualcuno che ha scritto un'applicazione GUI su larga scala e completa in C / C ++, non posso fare a meno di provare un senso di timore reverenziale e un pizzico di gelosia

Cattiva politica. Invece dovresti scoprire quali librerie di definizioni di classe hanno usato. Anche tu potresti usare quelle librerie.

Riguarda gli strumenti. Senza attrezzi, siamo solo animali nei pantaloni.

"C ++ nativo" non significa che dovresti buttare via tutti i tuoi strumenti. Significa che devi trovare buoni strumenti. Microsoft non ti aiuta più, quindi devi dedicare tempo a trovare il giusto mix di strumenti.


+1 per il "vai a scoprire cosa stanno usando", ma sinceramente penso che questo non sia molto bello per gli animali che usano strumenti, o animali che capita di indossare pantaloni in occasione.
Ian Pugsley,

@Ian Pugsley: gli animali che indossano i pantaloni ma non usano gli strumenti probabilmente stanno bene con il loro status di animali. Ma hai ragione sul fatto che gli animali che usano attrezzi senza pantaloni potrebbero arrabbiarsi. Mia moglie, ad esempio, preferisce non indossare i pantaloni e usa gli strumenti. Forse non leggerà questa domanda.
S.Lott

Possiamo solo sperare (e scommettere sulle possibilità abbastanza alte). Tutto quello che sto dicendo è che non guarderò in basso un animale abbastanza intelligente da indossare un paio di pantaloni ... per ogni evenienza.
Ian Pugsley,

Sì, a differenza della libreria standard di C #, quella di C ++ è vecchia e priva di esigenze moderne (GUI, interfaccia di rete interessante, ecc.).
Moshe Revah,

Microsoft ti aiuta ancora una volta con C ++ in Windows 8 (l'intera superficie di sviluppo di Windows 8 è un codice nativo e C ++ è un cittadino di prima classe insieme a C # e JavaScript): msdn.microsoft.com/en-us/library/windows/ app / ...
Zach,

5

Il problema qui non riguarda la programmazione hardcore o qualcosa del genere, riguarda il controllo. Il fatto è che C # offre produttività a un costo di controllo. Se stai scrivendo un programma che richiede un elevato controllo (questa memoria è stata allocata esattamente ora), allora non hai altra scelta che usare C ++. Se è necessario farlo rapidamente, potrebbe essere necessario utilizzare C #. Il problema è che le librerie di supporto per C # sono molto migliori e più recenti di quelle fornite per C ++. Ad esempio, MFC è molto, molto vecchio e le sue pratiche sono note per essere terribili, è stato per lo più scritto molto prima della standardizzazione. Se Microsoft si è impegnata a fornire nuove librerie C ++, ad esempio, controlla la nuova PPL in Visual Studio 2010, quindi stranamente, l'attività diventa semplice in C ++. E penso che stiano migrando in quel modo,

D'altra parte, il codice gestito ha garbage collector e l'ottimizzazione specifica della CPU e del sistema operativo in fase di runtime che può far funzionare il codice nativo per i suoi soldi.

Ho sentito molti sostenitori del linguaggio gestito dire questo, ma praticamente non l'ho mai visto come vero. Il fatto è che le nuove istruzioni CPU disponibili nelle CPU più recenti semplicemente non offrono un grande vantaggio a meno che tu non stia facendo matematica molto hardcore, nel qual caso non puoi permetterti il ​​sovraccarico di doverlo compilare o interpretarlo in esecuzione -time e potresti semplicemente usare il compilatore C ++ di Intel per utilizzare l'ultimo e il più grande in SSE comunque. Lo scopo delle ottimizzazioni del compilatore di C ++ è enorme rispetto a quello che può fare la JIT, perché la JIT deve essere eseguita in una frazione del tempo mentre il programma è in esecuzione, mentre i compilatori C ++ sono piuttosto leggendari per il loro dolce tempo per la compilazione.

La garbage collection non è una sorta di cosa magicamente eccezionale o qualcosa del genere: è una scelta di algoritmo. È appropriato per tutte le situazioni? Non guardare di gran lunga il disordine IDisposable in C # e come Java non si sia nemmeno preso la briga di provare con quel problema, mentre i distruttori di C ++ chiuderanno i tuoi file e libereranno la tua memoria e chiuderanno i tuoi socket, ecc. GC è ottimo per alcuni programmi e non per alcuni altri.


Ci sono molte differenze tra i processori rispetto a SIMD, sebbene il compilatore C ++ stia probabilmente prendendo in considerazione la pipeline tanto quanto la tua JIT.
Peter Taylor,

Un ambiente di runtime in cui è possibile esaminare lo stato del sistema e identificare ogni riferimento ad oggetti non appuntati che potrebbe mai essere raggiungibile può ammortizzare molti costi relativi a GC in modi che non sono possibili in C ++. In Java o C #, data String foo,bar;l'istruzione, foo=bar;verranno eseguite due istruzioni: un caricamento del registro e un archivio dei registri. Tempo di esecuzione costante indipendentemente dalla lunghezza della stringa. Il C ++ può avvicinarsi?
supercat,

2

A mio avviso il C / C ++ nativo, rispetto al C #, sembra un assemblatore allo stesso C / C ++. Un altro complesso livello di astrazione (non proprio vero, ma diciamo così) come sempre, ti dà uno sviluppo più semplice, ma una certa riduzione della velocità e un uso eccessivo della memoria. Quindi, per come la vedo io, si divide in diverse categorie, creando così nuovi sottotipi di programmatori.

A proposito del suo livello di astrazione, C # è incredibilmente veloce, Microsoft ha fatto un lavoro eccellente.


2

Ci sono programmatori amatoriali, non lingue amatoriali. Le lingue hanno tutte (beh, almeno la maggior parte di esse) il loro scopo.

Attualmente sto collaborando a un motore di calcolo assicurativo utilizzato per testare il sistema di produzione. Il sistema di produzione è stato realizzato in C, il nostro motore è realizzato in Java e da più tempo abbiamo sovraperformato il motore C, essendo allo stesso tempo molto più produttivo. Non perché Java di per sé sia ​​più veloce di C, è abbastanza veloce e i nostri algoritmi sono migliori, li abbiamo implementati più facilmente, potremmo testare e riformattare il nostro codice più velocemente e meglio.

Ho anche scritto un codice di prova per confrontare i risultati di calcolo con il contenuto del database di produzione: non in C, non in Java ma in Ruby. Ancora una volta, è abbastanza veloce e richiede molto meno codice, quindi è più facile da implementare, più facile da testare, più facile da espandere.

E non mi sento dilettante, indipendentemente dalla lingua che uso, mi sento così solo se creo un bug stupido che non avrebbe dovuto accadere.


1

L'anno scorso la ditta in cui lavoro stava eseguendo il reverse engineering di un codice CRC di comunicazioni per forza bruta (alla fine l'abbiamo ottenuto). 3 Gli sviluppatori avevano ciascuno la propria versione, Borland C, C # .Net 2008, VB6. Il VB6 era ovviamente lento, il Borland C era veloce ma il C # .net lo aveva appena frustato di 12 volte la velocità. Non era quello che ci aspettavamo affatto.


1
Stanno usando lo stesso algoritmo passo dopo passo? Potrebbero calcolare lo stesso output, ma i passaggi matematici elementari utilizzati per arrivare all'output potrebbero essere diversi e le prestazioni sono determinate dal conteggio grezzo dei passaggi elementari, che a sua volta è determinato da come la "formula" viene scomposta in essi.
rwong,

Un compilatore C meno recente potrebbe non utilizzare le ultime istruzioni del processore (ad esempio SSE2 e successive)
GrandmasterB

1
Tutte e tre le lingue vengono compilate in codice nativo ottimizzato (VB6 / C ++ durante la compilazione, .NET durante JIT). Quindi probabilmente stai misurando le differenze tra i tuoi programmatori piuttosto che tra i linguaggi di programmazione.
Nikie,

@nikie JIT! = compilation. E la qualità dei compilatori differisce. Ho visto esattamente lo stesso algoritmo eseguire molto più velocemente quando scritto in C ++ (nessuna chiamata API, solo riferimenti di array, loop e aritmetica semplice) rispetto a Java, nonostante tutti i discorsi su JIT.
quant_dev,

1
@quant_dev: Nella mia esperienza non esiste un proiettile d'argento ;-) La mia esperienza con .NET JIT è che la differenza tra JIT e MSVC ++ è molto piccola. Dubito fortemente 12x in entrambi i modi per lo stesso codice.
Nikie,

1

Dipende da un mix di cose, ma sostanzialmente, a parità di tutto il resto, sì, il codice nativo è più "hardcore" del codice gestito.

Immagino che di solito sia una brutta cosa, per una normale applicazione aziendale, perché significa che lo sviluppatore medio deve mettere più energia mentale negli aspetti non aziendali del proprio codice.


1

Il mio programma è ciò che potrebbe essere meglio descritto come C ++ come Java. La mia opinione è che puoi ottenere la stessa programmazione di basso livello in Java, ma è molto più difficile della programmazione di basso livello in C ++. Tuttavia, in genere è necessaria questa programmazione di basso livello in una piccola parte del codice e laddove non è richiesto un linguaggio gestito è più produttivo.


1

Gli sviluppatori nativi di solito hanno la reputazione di essere più hardcore perché si sentono più hardcore e agiscono in quel modo. Gli sviluppatori nativi sono addestrati in un sistema che non tollera alcun errore perché portano inevitabilmente a crash improvvisi o perdite di memoria illimitate. In particolare, .NET consente agli hack pigri come mettere a prova di tutto, evitando allo sviluppatore di pensare di dover capire il problema principale ("a volte, genera solo InvalidOperationException. Non posso spiegarlo, prendiamo semplicemente tutto. Questo il codice è fondamentale! "). Questo non è affatto in bianco e nero, ma le mie osservazioni sono cresciute nel mondo non gestito e ora lavorano a tempo pieno nel codice gestito.

Inoltre, gli sviluppatori gestiti tendono ad avere accesso a BCL molto più puliti e più organizzati. Questo spesso li incoraggia a esplorare ciò che realmente accade sotto le coperte. È vero, lo stesso si può dire per, diciamo, STL o Boost, ma la libreria di classi .NET è spesso abbastanza buona da renderci intellettualmente pigri a volte.

Detto questo, scrivere un buon programma gestito spedibile richiede molto lavoro. Ciò significa eseguire la profilazione della memoria e della CPU, unit test e analisi del codice in modo simile a quello degli sviluppatori non gestiti. Gli sviluppatori non gestiti tendono a capire ciò che accade e gli sviluppatori gestiti tendono a includere più di quelli che non lo fanno.

Ancora una volta, non in bianco e nero. Esistono molti sviluppatori non gestiti intellettualmente pigri e sviluppatori con gestione hardcore. Né è per definizione più elite dell'altra.


0

Vedi il codice gestito come amatoriale? Vedi i programmatori nativi come più hardcore?

C'è un divario tra i due mondi, e non riesco a capire perché: i sistemi gestiti sono scritti da qualche parte nel codice nativo (come ultimo, tutto gira "in assembly"). Quello che voglio vedere (ancora nella mia vita) è un sistema di costruzione di applicazioni, in cui tutte le attività secondarie dell'applicazione verranno scritte nel giusto tipo di lingua.


Un sistema di costruzione di applicazioni come descrivi è solo un altro (e si spera meglio) linguaggio di programmazione.
David Thornley,

Non ho familiarità con .NET, ma AFAIK è un sistema a linguaggio misto, che ha un formato eseguibile comune gestito da una macchina virtuale e una vasta libreria che può essere utilizzata con qualsiasi linguaggio .NET. Uno stesso sistema sarebbe bello nel mondo nativo / compilato. Indipendente dalla piattaforma, ovviamente.
ern0

0

Il codice nativo è diventato più facile da quando è stato rilasciato Go . Trovo più facile sia leggere che scrivere di Java e C #. Sebbene la programmazione della GUI con Go, al momento, non sia molto piacevole (ho dato una rapida occhiata alle opzioni).
Cerca di non giudicarlo per la sua mancanza di grande comunità e varietà di librerie rispetto a C # (ad esempio), perché è ancora considerato nuovo.

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.