Quali sarebbero le limitazioni del C ++ rispetto al linguaggio C? [chiuso]


116

Di seguito sono riportati i vantaggi di C ++

  • C ++ fornisce le funzionalità specifiche di cui chiedono
  • Il loro compilatore C è quasi certamente un compilatore C ++, quindi non ci sono implicazioni sui costi del software
  • Il C ++ è portabile quanto il C
  • Il codice C ++ può essere efficiente quanto C (o più o meno)

Ci sono ragioni concrete e scenari specifici, in cui è necessario utilizzare C su C ++?

Riferimento a questa domanda: Libreria per generici in C

Non è un duplicato, perché questa domanda riguarda i limiti della lingua e non il dovrebbe / non dovrebbe imparare una lingua rispetto a un'altra.

Il post di Peter Kirkham è stato per me il più informativo, in particolare per quanto riguarda le questioni C99 che non avevo considerato, quindi l'ho accettato. Grazie a tutti gli altri che hanno partecipato.


12
Non importa se questa domanda vuole essere polemica o no, lo è ancora. La scelta della lingua per un progetto è esattamente questo: una scelta.
Bombe

7
@bombe non dovremmo discutere su come fare scelte informate?



10
Non è ironico quando dai un consiglio ai programmatori C di passare a C ++ che sono più o meno ricettivi alla tua idea, come lo saresti se un programmatore C ti dicesse che dovresti abbandonare C ++ e passare a C?
Warren P

Risposte:


136

Ciò è richiesto da una risposta che ho dato a una domanda corrente che chiede di una libreria generics per C - l'interrogante afferma specificamente che non vogliono usare C ++.

C è un linguaggio di programmazione completo. C non è un sottoinsieme arbitrario di C ++. C non è affatto un sottoinsieme di C ++.

Questo è valido C:

foo_t* foo = malloc ( sizeof(foo_t) );

Per farlo compilare come C ++ devi scrivere:

foo_t* foo = static_cast<foo_t*>( malloc ( sizeof(foo_t) ) );

che non è più valido C. (potresti usare il cast in stile C, nel qual caso si compilerebbe in C, ma verrebbe evitato dalla maggior parte degli standard di codifica C ++ e anche da molti programmatori C; guarda i commenti "non lanciare malloc" in tutto Stack Overflow) .


Non sono la stessa lingua e se hai un progetto esistente in C non vuoi riscriverlo in una lingua diversa solo per usare una libreria. Preferiresti usare le librerie con cui puoi interfacciarti nella lingua in cui stai lavorando (in alcuni casi questo è possibile con alcune extern "C"funzioni wrapper, a seconda di come è template / inline una libreria C ++).

Prendendo il primo file C in un progetto su cui sto lavorando, questo è ciò che accade se effettui lo scambio gcc std=c99con g++:

sandiego:$ g++ -g  -O1 -pedantic -mfpmath=sse -DUSE_SSE2 -DUSE_XMM3  -I src/core -L /usr/lib -DARCH=elf64 -D_BSD_SOURCE -DPOSIX -D_ISOC99_SOURCE -D_POSIX_C_SOURCE=200112L -Wall -Wextra -Wwrite-strings -Wredundant-decls -Werror -Isrc  src/core/kin_object.c -c -o obj/kin_object.o | wc -l
In file included from src/core/kin_object.c:22:
src/core/kin_object.h:791:28: error: anonymous variadic macros were introduced in C99
In file included from src/core/kin_object.c:26:
src/core/kin_log.h:42:42: error: anonymous variadic macros were introduced in C99
src/core/kin_log.h:94:29: error: anonymous variadic macros were introduced in C99
...
cc1plus: warnings being treated as errors
src/core/kin_object.c:101: error: ISO C++ does not support the z printf length modifier
..
src/core/kin_object.c:160: error: invalid conversion from void*’ to kin_object_t*’
..
src/core/kin_object.c:227: error: unused parameter restrict
..
src/core/kin_object.c:271: error: ISO C++ does not support the z printf length modifier
src/core/kin_object.c:271: error: ISO C++ does not support the z printf length modifier

In totale 69 righe di errore, quattro delle quali sono conversioni non valide, ma principalmente per funzionalità che esistono in C99 ma non in C ++.

Non è che sto usando queste funzionalità per il gusto di farlo. Ci vorrebbe un lavoro significativo per portarlo in una lingua diversa.

Quindi è assolutamente sbagliato suggerirlo

[a] Il compilatore C è quasi certamente un compilatore C ++, quindi non ci sono implicazioni sui costi del software

Ci sono spesso significative implicazioni di costo nel portare il codice C esistente al sottoinsieme procedurale di C ++.

Quindi suggerire 'usa la classe C ++ std :: queue' come risposta alla domanda che cerca un'implementazione della libreria di una coda in C è dafter che suggerire 'usa l'obiettivo C' e 'chiama la classe Java java.util.Queue usando JNI' o 'chiama la libreria CPython' - Objective C è effettivamente un superset appropriato di C (incluso C99), e le librerie Java e CPython sono entrambe richiamabili direttamente da C senza dover trasferire codice non correlato al linguaggio C ++.

Ovviamente potresti fornire una facciata C alla libreria C ++, ma una volta che lo fai, C ++ non è diverso da Java o Python.


21
Sì. Il cast in stile C è abbastanza normale quando usi malloc. Quando usi malloc, rimani nel sottoinsieme c. Se vuoi programmare lo stile C ++, dovresti usare l'operatore new, non static_cast + malloc.
Suma

33
Dire che C non è un sottoinsieme di C ++ è incredibilmente pedante. Certo, si potrebbe dire che qualsiasi struttura con un membro chiamato "classe" non verrà compilata, ma in realtà sono necessarie solo piccole modifiche e la maggior parte dei compilatori ha opzioni per aggiungere le poche funzionalità solo C a C ++.
Kaz Dragon,

27
per quanto riguarda il tuo esempio malloc, l'aggiunta di un cast non sarebbe evitata solo dai programmatori C ++, ma anche (soprattutto) dai programmatori C. Ci sono buone ragioni per tralasciare il cast nel codice C. Non è necessario e aggiungerlo potrebbe nascondere gli errori. Quindi sì, trattali come due lingue distinte. +1 :)
jalf

26
@BlueRaja Immagina se Guido avesse deciso di non aggiungere oggetti al suo linguaggio di scripting e due gruppi avessero creato fork di Python reciprocamente incompatibili per aggiungere oggetti, uno con un modello di oggetti basato su Smalltalk, l'altro con un sistema di classi basato su Simula. Poi Guido ha continuato a migliorare Python concentrandone l'utilizzo principale. È più vicino alla situazione C / Objective C / C ++.
Pete Kirkham

11
@BlueRaja: sono due lingue distinte che condividono un nucleo comune abbastanza ampio. Se programmi in quel nucleo comune, finirai per fare cose che non sono un buon codice in nessuna delle due lingue. Scegli una lingua in cui scrivere un determinato programma e fallo bene in quella lingua.
David Thornley

115

Mi rendo conto che non è né una risposta professionale né particolarmente buona, ma per me è semplicemente perché mi piace molto C.C è piccolo e semplice e posso adattare l'intero linguaggio nel mio cervello, C ++ a me è sempre sembrato un enorme pasticcio tentacolare con tutti i tipi di strati ho difficoltà a grokking. Per questo motivo scopro che ogni volta che scrivo C ++ finisco per passare molto più tempo a fare il debug e sbattere la testa contro superfici dure rispetto a quando codice C. Di nuovo mi rendo conto che molto di questo è in gran parte il risultato della mia "ignoranza".

Se posso scegliere scriverò tutte le cose di alto livello come l'interfaccia e l'interazione con il database in Python (o forse C #) e tutte le cose che devono essere veloci in C. Per me questo mi dà il meglio di tutti i mondi. Scrivere tutto in C ++ è come avere il peggio di tutti i mondi.

Modifica: vorrei aggiungere che penso che il C con alcune funzionalità C ++ sia in gran parte una cattiva idea se ci saranno diverse persone che lavorano su un progetto o se la manutenibilità è la priorità. Ci sarà disaccordo su ciò che costituisce un "pochi" e quali bit dovrebbero essere fatti in C e quali bit in C ++ portando alla fine a una base di codice molto schizofrenica.


24
Ho usato C ++ per diversi anni e ancora ho passato il 50% del mio tempo a refactoring del codice per essere "C ++ corretto". È un incubo, come dici tu.
Kai,

12
Potresti sempre farlo bene la prima volta. L'aggiunta di const non è difficile.
GManNickG

14
Ho usato C ++ per dieci anni e tornare a C (per i sistemi embedded nel mio caso) è stata la cosa migliore che abbia mai fatto.
Warren P

Amo questa risposta. Hai inchiodato anche i miei sentimenti. Ho lavorato per anni come sviluppatore C ++, il mio lavoro quotidiano è ancora C ++. Ma questo non significa che mi piaccia la lingua, vedo la bellezza in C.
Matt Joiner

10
1, A causa di questo trovo che ogni volta che scrivo C ++ finisco per spendere molto più tempo di debug e sbattendo la testa contro superfici dure rispetto a quando il codice I C . Non posso essere più d'accordo con te. La migliore risposta. :)
ApprenticeHacker

58

Il C ++ semplicemente non è supportato in alcuni ambienti del mondo reale, come i sistemi embedded di basso livello. E c'è una buona ragione per questo: C facilmente abbastanza buono per queste cose, quindi perché usare qualcosa di più grande?


2
Destra. Ho visto compilatori c per micro controller a 8 bit.
dmckee --- gattino ex moderatore

6
ovviamente. La maggior parte se non tutti i chip a 8 bit hanno compilatori C in questi giorni.
Eli Bendersky,


+1 questa è la risposta corretta. I compilatori C ++ sono molto più difficili da scrivere rispetto ai compilatori C, in gran parte a causa della complessità dell'ereditarietà (multipla).
BlueRaja - Danny Pflughoeft

9
@BlueRaja: rispetto ai modelli ... l'ereditarietà multipla potrebbe non essere il vero deterrente qui. Dopotutto, i modelli costituiscono un proprio linguaggio a tutti gli effetti.
Matthieu M.

49

Odio programmare in C ++.


6
Lol Mi piace quello
Tamas Czinege

30
Molto convincente! Sto pensando di passare a Python in base al tuo argomento.
Jimmy J

8
Forse non convincente, ma è il vero motivo.
Georg Schölly

@ Jimmy J: Python è incredibile. È il meglio di Unix, C e di tutte le funzionalità del tuo linguaggio "moderno" fatto bene. Se hai problemi di prestazioni Python vuole che tu passi a C e lo fa facilmente.
Matt Joiner

2
@ Georg: ammetto di non aver mai dato un'occhiata, sono così impressionato da Python.
Matt Joiner

38

Un paio di ragioni potrebbero essere:

  • Mancanza di supporto: non tutti i compilatori C sono anche compilatori C ++. Non tutti i compilatori sono particolarmente conformi allo standard, anche se affermano di supportare C ++. E alcuni compilatori C ++ generano codice irrimediabilmente gonfio e inefficiente. Alcuni compilatori hanno terribili implementazioni della libreria standard. Lo sviluppo in modalità kernel generalmente rende impossibile l'uso della libreria standard C ++, così come alcune funzionalità del linguaggio. Puoi ancora scrivere codice C ++ se ti attieni al nucleo del linguaggio, ma potrebbe essere più semplice passare a C.
  • Familiarità. Il C ++ è un linguaggio complesso. È più facile insegnare a qualcuno il C che il C ++ ed è più facile trovare un buon programmatore C che un buon programmatore C ++. (la parola chiave qui è "buono". Ci sono molti programmatori C ++, ma la maggior parte di loro non ha imparato il linguaggio correttamente)
  • Curva di apprendimento - Come sopra, insegnare a qualcuno il C ++ è un compito enorme. Se stai scrivendo un'app che deve essere mantenuta da altri in futuro, e questi altri potrebbero non essere programmatori C ++, scriverla in C rende molto più facile affrontarla.

Preferirei comunque scrivere in C ++ quando posso farla franca e, nel complesso, penso che i vantaggi superino gli svantaggi. Ma posso anche vedere l'argomento per l'utilizzo di C in alcuni casi.


4
Aggiungerei che il codice C si compila molto più velocemente di C ++. Un progetto enorme nella nostra azienda (più di un milione di righe) viene compilato in meno di 30 secondi.
Calmarius

31

Ci sono un sacco di argomenti sulla programmazione incorporata, sulle prestazioni e cose del genere, non li compro. Il C ++ si confronta facilmente con il C in quelle aree. Però:

Proprio di recente, dopo aver programmato in C ++ per oltre 15 anni, sto riscoprendo le mie radici in C. Devo dire che mentre ci sono buone caratteristiche in C ++ che rendono la vita più facile, ci sono anche un sacco di insidie ​​e una sorta di "c'è-sempre-un-modo-migliore" di fare le cose. Non sei mai veramente felice della soluzione che hai fatto. (Non fraintendetemi, questa potrebbe essere una buona cosa, ma soprattutto no).

Il C ++ ti dà sparatorie infinite. Il che potrebbe essere probabilmente buono, ma in qualche modo finisci sempre per usarne troppo. Ciò significa che stai mascherando le tue soluzioni con strati "belli" e "graziosi" di astrazioni, generalità, ecc.

Quello che ho scoperto tornando a C è stato che in realtà era di nuovo divertente programmare. Avendo passato così tanto tempo a modellare e pensare a come utilizzare al meglio l'ereditarietà, trovo che programmare in C in realtà renda il mio codice sorgente più piccolo e più leggibile. Questo ovviamente dipende dal tuo livello di autodisciplina. Ma è molto facile mettere troppe astrazioni su un codice diretto, che non è mai effettivamente necessario.


8
Senza offesa, ma potrebbe anche dipendere da ciò che pensi sia C ++. L'ereditarietà è qualcosa che associo più a Java che a C ++, e se tratti il ​​C ++ rigorosamente come un linguaggio OOP come Java (C con classi), allora sono d'accordo con te. Se ti attieni a un gusto più moderno di C ++, penso che sia più divertente di C
jalf

11
Ancora una volta, però, non penso al C ++ come a un linguaggio OO e non dovrebbe essere trattato come tale. Penso che la programmazione generica sia una caratteristica molto più forte del C ++. La maggior parte del codice C ++ che vedo non si sforza particolarmente di essere "OO" o contiene codice non necessario. È spesso più snello del codice C equivalente
jalf

3
@jalf: Un'altra cosa che trovo possa diventare una distrazione "c'è-sempre-una-via migliore" in C ++ è generalizzare le cose con i modelli. "Forse dovremmo lasciare che l'utente di questa classe decida quale tipo di intero sottostante usare?" Ma probabilmente non ne hai bisogno , e in C non ti preoccuperesti. E a volte mi ritrovo a pensare, "Dovremmo davvero fornire un'interfaccia iteratore in avanti a questa classe", quando in C esporesti semplicemente un puntatore al primo elemento e un conteggio, o (l'altezza della fantasia!) Una funzione che prende una puntatore a funzione di callback.
j_random_hacker

2
Trovo che fare un passo indietro quando la codifica in C ++ aiuta. Decidi l'obiettivo e scrivi verso di esso (stile C). Fattore negli ismi C ++ quando la loro utilità diventa evidente.
Matt Joiner

2
infinite gunfire, ooh sì, così vero. I nostri piedi tremano letteralmente :)
quetzalcoatl

27

C ha il vantaggio principale di poter vedere cosa sta realmente succedendo quando guardi un pezzo di codice (sì preprocessore: compila con -E e poi lo vedi). Qualcosa che troppo spesso non è vero quando guardi del codice C ++. Lì hai costruttori e distruttori che vengono chiamati implicitamente in base all'ambito oa causa di assegnazioni, hai un sovraccarico di operatori che può avere un comportamento sorprendente anche quando non viene utilizzato in modo improprio. Ammetto di essere un maniaco del controllo, ma sono giunto alla conclusione che questa non è una cattiva abitudine per uno sviluppatore di software che vuole scrivere software affidabile. Voglio solo avere una buona possibilità di dire che il mio software fa esattamente quello che dovrebbe fare e allo stesso tempo non ha una brutta sensazione allo stomaco perché so che potrebbero esserci ancora così tanti bug che non lo farei '

C ++ ha anche modelli. Li odio e li amo, ma se qualcuno dice che li capisce completamente lo chiamo bugiardo! Ciò include gli autori del compilatore e le persone coinvolte nella definizione dello standard (che diventa ovvio quando si tenta di leggerlo). Ci sono così tanti casi d'angolo assurdamente fuorvianti coinvolti che semplicemente non è possibile considerarli tutti mentre scrivi codice reale. Adoro i modelli C ++ per la loro pura potenza. È davvero sorprendente quello che puoi fare con loro, ma allo stesso modo possono portare agli errori più strani e difficili da trovare che uno non può (non) immaginare. E questi errori si verificano effettivamente e non di rado. Leggere le regole coinvolte per risolvere i modelli in C ++ ARM mi fa quasi esplodere la testa. E mi dà la brutta sensazione di perdere tempo a dover leggere messaggi di errore del compilatore lunghi diversi 1000 caratteri per i quali ho bisogno già di 10 minuti o più per capire cosa il compilatore vuole effettivamente da me. Nel tipico codice C ++ (libreria) spesso trovi anche molto codice nei file di intestazione per rendere possibili determinati modelli che a sua volta rende i cicli di compilazione / esecuzione dolorosamente lenti anche su macchine veloci e richiede la ricompilazione di grandi parti del codice quando cambi qualcosa Là.

C ++ ha anche la trappola const. O eviti const per tutti tranne i casi d'uso più banali o prima o poi dovrai scartarlo o rifattorizzare gran parte del codice base quando si evolve, specialmente quando stai per sviluppare un design OO piacevole e flessibile.

Il C ++ ha una digitazione più forte del C, il che è fantastico, ma a volte mi sembra di alimentare un Tamagotchi quando provo a compilare codice C ++. Gran parte degli avvisi e degli errori che di solito ricevo da esso non sono realmente io che faccio qualcosa che non funzionerebbe, ma solo cose che il compilatore non vuole che io faccia in questo modo o no senza eseguire il casting o inserire alcune parole chiave extra qui e Là.

Questi sono solo alcuni dei motivi per cui non mi piace il C ++ per il software che scrivo da solo utilizzando solo alcune librerie esterne presumibilmente robuste. Il vero orrore inizia quando scrivi codice in team con altre persone. Quasi non importa se sono hacker C ++ molto intelligenti o principianti ingenui. Tutti commettono errori, ma il C ++ rende deliberatamente difficile trovarli e ancora più difficile individuarli prima che si verifichino.

Con C ++ sei semplicemente perso senza usare un debugger tutto il tempo ma mi piace poter verificare la correttezza del mio codice nella mia testa e non dover fare affidamento su un debugger per trovare il mio codice in esecuzione su percorsi che non avrei mai previsto. In realtà cerco di eseguire tutto il mio codice nella mia testa e cerco di prendere tutti i rami che ha, anche nelle subroutine ecc. E di usare un debugger solo occasionalmente solo per vedere come funziona bene attraverso tutti i posti accoglienti che ho preparato per esso. Scrivere ed eseguire così tanti casi di test che tutti i percorsi del codice sono stati utilizzati in tutte le combinazioni con tutti i tipi di strani dati di input è semplicemente impossibile. Quindi potresti non conoscere i bug nei programmi C ++, ma ciò non significa che non siano presenti. Più grande diventa un progetto C ++, minore diventa la mia fiducia che non avrà molti bug non rilevati anche se funziona perfettamente con tutti i dati di test che abbiamo a portata di mano. Alla fine lo cestino e ricomincio da capo con un'altra lingua o una combinazione di altre lingue.

Potrei andare avanti ma credo di aver già chiarito il mio punto di vista. Tutto questo mi ha fatto sentire improduttivo quando programma in C ++ e mi ha fatto perdere la fiducia nella correttezza del mio codice, il che significa che non lo userò più, mentre uso ancora e mi affido al codice C che ho scritto più di 20 anni fa. Forse è semplicemente perché non sono un buon programmatore C ++, o forse essere abbastanza bravo in C e altri linguaggi mi permette di riconoscere quanto sono veramente un lamer quando si tratta di C ++, e che non sarò mai in grado di comprenderlo appieno .

La vita è breve...


2
+1, non potrei essere più d'accordo.
missingfaktor

2
Questo suona notevolmente parallelo all'argomento di Linus. (Meno di un contesto oggetto = più facile da capire.)
Warren P,

20

In un ambiente embedded di basso livello alcuni degli "ingegneri del software" avranno un background EE e avranno a malapena padroneggiato il C. C ++ è più complesso e alcuni di questi ragazzi hanno semplicemente paura di imparare una nuova lingua. Quindi C è usato come il minimo comune denominatore. (Prima di suggerire di sbarazzarsi di questi ragazzi, sono almeno tanto importanti quanto i maggiori CS che non capiscono la roba analogica hardcore.)

Parlando per esperienza nell'aver ereditato e mantenuto entrambi: un design orribile in C è difficile da capire, srotolare e refactoring in qualcosa di utilizzabile.

Un progetto orribile in C ++ è infinitamente peggiore poiché strati casuali di astrazione mandano il tuo cervello a sbandare intorno alla base del codice cercando di capire quale codice verrà eseguito in quale circostanza.

Se devo lavorare con ingegneri che so che non produrranno grandi progetti, preferirei di gran lunga il primo piuttosto che il secondo.


Amen, fratello. Avendo lavorato con il sorgente C prodotto da ingegneri hardware, rabbrividisco al pensiero a cosa mi sarei dovuto affrontare se lo avessero fatto in C ++.
Richard Chambers,

19

Non vedo altre ragioni oltre all'antipatia personale, anche per la programmazione di sistemi embedded e cose simili. In C ++ paghi le spese generali solo per le funzionalità che utilizzi. È possibile utilizzare il sottoinsieme C del C ++ in alcune situazioni specifiche in cui l'overhead C ++ è troppo alto per te. Detto questo, penso che alcuni programmatori C sovrastimano il sovraccarico di alcuni costrutti C ++. Vorrei elencare alcuni esempi:

  • Le classi e le funzioni membro hanno zero overhead rispetto alle funzioni normali (a meno che non si utilizzino funzioni virtuali, nel qual caso non vi è overhead rispetto all'utilizzo di puntatori a funzioni)
  • I modelli hanno un sovraccarico minimo (molto spesso nessun sovraccarico)

Un motivo valido potrebbe essere quando si sta programmando per una piattaforma che non dispone di un compilatore C ++ decente (nessun compilatore C ++ o esiste un compilatore, ma è mal implementato e impone un overhead elevato non necessario per alcune funzionalità C ++).


3
Una classe con funzioni virtuali ha più overhead: ogni istanza deve portare in giro un campo extra per identificare il tipo.
bstpierre

6
Più sovraccarico di cosa? Il tipo viene trasportato nel vtbl. Se si implementa un meccanismo simile utilizzando i puntatori a funzione, è necessario almeno un puntatore (o indice o qualsiasi altra cosa) per selezionare il puntatore a funzione che si desidera utilizzare.
Suma

3
bstpierre: Penso che quello che sta dicendo Suma sia: che non ha più overhead dell'implementazione della funzione manualmente in C.
Martin York

2
Un puntatore alle classi vtable è memorizzato in ogni istanza della classe.
tstenner

5
C'è un sovraccarico, ma quello che voglio dire è che se vuoi una risoluzione di tipo dinamico, hai bisogno di un po 'di spazio di archiviazione per identificare il tipo, anche in C.Se non vuoi i tipi dinamici, non devi pagare l'overhead ( non usare funzioni virtuali se non ti servono).
Suma

13

Perché limitare il parlare in inglese? Forse saresti un autore più creativo in serbo.

Questo è lo stesso argomento, con evidenti errori. Se hai un compito e i tuoi comodi strumenti risolvono il compito in modo efficiente, probabilmente utilizzerai i tuoi comodi strumenti per una buona ragione.


3
Se parlassi fluentemente inglese e fluente serbo, sono sicuro che sarei più creativo. Non sei d'accordo?

2
@Neil in effetti, ma lo sforzo richiesto per imparare il serbo potrebbe non essere giustificato per risolvere il mio attuale blocco di creatività.
magro

2
Penso che Arno stia evidenziando il fatto che non stai scrivendo per la CPU, stai scrivendo perché i tuoi colleghi leggano e le tue altre librerie da collegare e così via. Dopotutto, se cercassi solo espressività e velocità, scriverei in OCaml.
Ken

10

Il C ++ ha una curva di apprendimento molto più lunga. C ha solo pochi costrutti di cui devi essere a conoscenza, quindi puoi iniziare a scrivere codice potente. In C ++ devi imparare la base C, quindi l'OO e la programmazione generica, eccezioni, ecc. E dopo un po 'potresti conoscere la maggior parte delle funzionalità e puoi possibilmente usarle, ma non sai ancora come farà il compilatore tradurli, quale sovraccarico implicito hanno o no. Questo richiede molto tempo ed energia.

Per un progetto professionale questo argomento potrebbe non contare, perché puoi assumere persone che già conoscono molto bene il C ++. Ma nei progetti Open Source, dove il C è ancora ampiamente utilizzato, le persone scelgono la lingua che preferiscono e sono in grado di utilizzare. Considera che non tutti i programmatori di sistemi operativi sono programmatori professionisti.


1
Ehm ... no? Impari la base C (possibilmente con l'eccezione degli array e la gestione delle stringhe in stile C abbandonata a favore di <vector> e <string>), e vai avanti. Puoi raccogliere tutto il resto mentre procedi. Non devi sapere nulla di OO, GP o eccezioni per iniziare con C ++ ...
DevSolar

4
C può essere "più piccolo" ma a lungo termine non è più facile da usare. Gestione manuale della memoria? No grazie.
Jimmy J

7
Non esiste una cosa come la gestione automatica della memoria in C ++.
Warren P

3
Il C ++ non risolve il problema di gestione della memoria. Proprio quando pensavi di avere un controllo sui puntatori, C ++ aggiunge un orribile modello di eccezione. Vieni nel mondo del C99, ad eccezione delle strutture dati, sono abbastanza certo di toccare a malapena malloc. Anche allora posso "incapsulare" una manciata di chiamate malloc. È più o meno la stessa storia in C ++ (gestione della memoria implicita, solo che viene eseguita sull'heap invece che sullo stack), solo con tutto il jazz puntatore intelligente.
Matt Joiner

1
@ereOn: È vero, il commento come l'ho scritto 3 anni fa non regge più. :)
Matt Joiner

10

Vorrei dare seguito alla risposta di Dan Olson. Credo che le persone temano le funzionalità potenzialmente pericolose e controproducenti del C ++, e giustamente. Ma a differenza di quanto dice Dan, non credo che la semplice decisione su uno standard di codifica sia efficace, per due ragioni:

  1. Gli standard di codifica possono essere difficili da applicare rigorosamente
  2. Può essere molto difficile trovarne uno buono.

Penso che la seconda ragione qui sia molto più importante della prima, perché la decisione su uno standard di codifica può facilmente diventare una questione politica ed essere soggetta a revisione in seguito. Considera il seguente caso semplificato:

  1. Puoi usare contenitori stl, ma non usare modelli in nessuno dei tuoi codici.
  2. Le persone iniziano a lamentarsi del fatto che sarebbero più produttive se solo fosse consentito codificare questa o quella classe modello.
  3. Lo standard di codifica è stato rivisto per consentirlo.
  4. Far scorrere un pendio verso uno standard di codifica eccessivamente complicato che nessuno segue e utilizzare esattamente il tipo di codice pericoloso che lo standard avrebbe dovuto impedire, combinato con l'eccessiva burocrazia che circonda lo standard.

(L'alternativa che lo standard non viene rivisto nel passaggio 3 è empiricamente troppo improbabile da considerare e comunque non sarebbe molto migliore.)

Anche se alcuni anni fa usavo C ++ per quasi tutto, comincio a sentire fortemente che C è preferibile nelle attività di basso livello che devono essere gestite da C o C ++ e tutto il resto dovrebbe essere fatto in qualche altro lingua interamente. (Le uniche eccezioni possibili sono alcuni domini con problemi specifici ad alte prestazioni, rispetto a Blitz ++ )


10

Uso C, o almeno esporto un'interfaccia C quando scrivo il codice della libreria.

Non voglio fastidi ABI mal definiti.


Stesso. C rigoroso solo nelle interfacce. L'ultima cosa che voglio è che il ridicolo quadro di oggetti di qualcun altro mi venga spinto addosso.
Matt Joiner

9

Non ho mai visto argomenti per l'utilizzo di C su C ++ che considererei convincente. Penso che la maggior parte delle persone abbia paura di alcune funzionalità offerte da C ++, spesso in modo giustificato. Eppure questo non mi convince perché si può imporre se utilizzare o meno determinate funzionalità tramite standard di codifica. Anche in C, c'è molto che vorresti evitare. Scartare completamente il C ++ significa essenzialmente dire che non offre vantaggi tangibili su C che aiuterebbero a scrivere codice migliore, che è una visione che considero piuttosto ignorante.

Inoltre, le persone sembrano sempre sollevare la situazione delle piattaforme in cui non esiste un compilatore C ++. Certamente C sarebbe appropriato qui, ma penso che sarebbe difficile trovare una piattaforma del genere in questi giorni.


3
D'accordo, le invettive "C è migliore di C ++" non reggono mai al controllo.
Jimmy J

6
Credo che il C ++ mi offra MOLTO PICCOLI vantaggi, e MI COSTA un'enorme quantità di complessità accidentale. Credo che ci vorrebbero circa 1500 pagine di libri di testo C ++ e dieci anni di impegno per diventare abile in C ++ come lo sono attualmente in C, Pascal, Python e Objective-C. Ciascuno dei linguaggi di cui sopra è circa 20 volte più ortogonale, compatto e mentalmente comodo da usare, per non parlare di più potente, negli ambienti in cui li uso. Semplicemente NON ci sono usi razionalmente giustificabili per C ++ nei miei soliti ambienti di sviluppo.
Warren P

@ Warren Paghi solo per quello che usi, proprio come qualsiasi lingua. Se non sei in grado di decidere come programmare saggiamente in C ++, dipende da te, non dal linguaggio.
Dan Olson,

2
Non così. Se sei l'unico sviluppatore di un progetto, potrebbe essere così. Ma non appena abbiamo due sviluppatori, abbiamo battaglie. Che cosa? Insisti sui contenitori IoC, mentre io preferisco un altro modo di fare i delegati ... Ti piacciono tre livelli di modelli annidati e io preferisco zero modelli. Un casino.
Warren P

So che questo post risale a 10 anni fa, ma è davvero giusto confrontare ancora C e C ++? Sono entrambe lingue separate e divergenti (dal C99) ed entrambe hanno i loro vantaggi e svantaggi che ciascuna copre. C ++ è difficile da eseguire il debug e da mantenere? L'esplicita 'di C ti permette di eseguire il debug meglio. C non ha farmaci generici? Il C ++ ha dei generici! A questo punto, nessuna lingua è migliore dell'altra.
Nergal

9

Un punto che non ho ancora visto sollevato, che penso sia il più importante:

La maggior parte delle librerie che uso quotidianamente sono librerie C con collegamenti per Python, Ruby, Perl, Java, ecc. avvolgere le librerie C ++.

Ad esempio, ho imparato il Cairo una volta e da allora l'ho usato in 3 o 4 lingue diverse. Grande vincita! Preferisco scrivere un programma che possa essere riutilizzato in futuro, e scriverne uno che possa essere facilmente adottato da altri linguaggi di programmazione ne è un caso estremo.

So che è possibile associare le librerie C ++, ma AFAICT non è la stessa cosa. Ho usato Qt (v3 e v4) in altre lingue e non è neanche lontanamente piacevole da usare: hanno voglia di scrivere C ++ in qualche altro linguaggio, non come le librerie native. (Devi passare le sigle del metodo C ++ come stringhe!)

C ++ è probabilmente un linguaggio migliore se stai scrivendo una funzione da utilizzare una sola volta o se pensi che tutto il mondo sia C ++. Il C sembra un linguaggio più semplice se stai progettando per la portabilità del linguaggio sin dall'inizio.


Il "passaggio metodi come stringhe!" cosa è un difetto di Qt, non C ++. Potresti effettivamente avere lo stesso stupido meccanismo con un framework C che vorresti. Anche i ragazzi di Qt concordano sul fatto che è stato un errore. Non c'era alternativa migliore nella loro mente in quel momento ed era troppo tardi per cambiarla quando si resero conto.
ereIl

7

Lo sviluppo del kernel di Windows non supporta c ++ (purtroppo).


Com'è? Perché? Il binario prodotto da un compilatore C ++ è diverso da un compilatore C? Lo sviluppo dei driver non sta semplicemente aderendo alle API?
Dave Van den Eynde

4
Perché molte funzionalità C ++ richiedono il supporto del runtime che potrebbe non essere banale da implementare in modalità kernel. Per prima cosa, vengono utilizzate diverse funzioni di allocazione della memoria, quindi è necessario sostituire parti della libreria standard. Anche le eccezioni sono generalmente negative.
jalf

3
Aggiungerò che Linux Torvalds ha fortunatamente bruciato ogni possibilità di C ++ in Linux per più ragioni che eccezioni. Ci sono stati alcuni sistemi operativi in ​​altri linguaggi: Java, C ++, assembler. Solo quelli assemblatori sono sopravvissuti con un uso ragionevole.
Matt Joiner


Hai notato che è per Visual Studio 2015?
LegendLength

6

Puoi leggere un divertente sproloquio sul perché Linus Torvalds preferisce C qui


6
È più uno sfogo semi-coerente contro il design orientato agli oggetti che uno sfogo contro C ++.
Dan Olson

16
Il signor Torvalds ha una lunga lista di cose che non gli piacciono, C ++, emacs, Subversion, OO per citarne alcune. Uno a volte vuole tasto avrebbe fatto il labbro un po 'di più

11
A Linus piace inveire e cercare di provocare e turbare le persone. Sfortunatamente, non si è preoccupato di imparare il C ++ prima di dichiarare che fa schifo. Sfortunatamente, i suoi seguaci credono che tutto ciò che dice debba essere vero.
jalf

9
Il collegamento era più per l'intrattenimento che per l'istruzione
Paul Dixon

6
Prova che anche i geni a volte possono essere stupidi.
Kaz Dragon

5

Il codice nativo su un Mac è Objective-C. Il codice nativo su un PC è c (window.h) o c ++ (mfc). Entrambi questi ambienti ti permetteranno di usare c con poche o nessuna modifica. Quando voglio che una libreria di codice sia multipiattaforma, ansi c sembra una buona scelta.


4

Mi vengono in mente diversi motivi.

Potrebbe non esserci un compilatore C ++ soddisfacente. Il C ++ è un linguaggio molto più grande e ho eseguito compilatori C su sistemi che non sarebbero in grado di gestire il C ++ moderno.

L'interrogante, o le persone con cui lavora, potrebbe avere familiarità con C ma non C ++.

Il progetto potrebbe essere in C. Sebbene sia possibile aggiungere alcune funzionalità C ++ a C, ciò può facilmente portare a un pasticcio non gestibile. Suggerirei di scegliere una lingua o l'altra (di solito C ++, quando pratico).

L'interrogante potrebbe avere una visione obsoleta della curva di apprendimento di C ++. (Se affrontato correttamente, è più facile di C. La maggior parte dei libri introduttivi che ho visto non si avvicina correttamente.)

Ricorda che C e C ++ sono due linguaggi diversi e stanno diventando sempre più diversi nel tempo. La codifica in entrambi contemporaneamente è una cattiva idea e l'utilizzo di un sottoinsieme C-like di C ++ perde la maggior parte dei vantaggi di C ++.


3

Se lavori in un ambiente con due linguaggi, potresti usare C per alcune funzioni di basso livello critiche per le prestazioni e un linguaggio più funzionale / di alto livello come C # / Java per la logica di business. Se viene utilizzato codice C ++ per queste funzioni, sono necessari C-wrapper per JNI / codice non gestito e questo rende le cose più complesse rispetto all'uso esclusivo di C.


3

Uso C ++ con la programmazione C per due motivi:

  • vectore stringper allontanarmi dalla gestione della memoria dell'array
  • rigoroso controllo del tipo e cast per avvertire e / o rilevare tutti i fastidi che altrimenti mi perderei.

Quindi è il C che prende in prestito un po 'di C ++ ma usa il compilatore C ++ il più possibile. Come qualcun altro dice nelle risposte, trovo che ora sto effettivamente raccogliendo più C ++ in questo modo e dove C sarebbe troppo coinvolgente, io uso C ++. Monitor / Lock using RAII è uno di questi che ho usato di recente quando si tratta di programmi multi-thread e un altro costrutto simile per aprire / chiudere i file.


3

Penso che C sia più portabile. Ho fatto un po 'di lavoro circa 5 anni fa portando il codice a molte versioni di unix (AIX, Irix, HPUX, Linux). Il codice C è stato facile da trasferire, ma abbiamo avuto vari problemi durante il trasferimento di parte del codice C ++. Forse erano solo ambienti di sviluppo immaturi, ma preferirei di gran lunga usare C su C ++ per questo motivo ...


1
Quindici anni fa ero lo sviluppatore principale di un progetto C ++ rivolto a HPUX, AIX e Solaris. Abbiamo avuto pochissimi problemi di portabilità C ++ - quasi tutti quelli che abbiamo avuto erano con le incompatibilità delle chiamate di sistema C.

1
Meno di dieci anni fa, ero a un progetto che utilizzava HPUX, Solaris e Tru64, utilizzando i compilatori tradizionali. I nostri nightlies non sono mai stati costruiti. Quando abbiamo aggiunto AIX, abbiamo deciso di passare al C ++ standard.
David Thornley

Forse le persone che hanno scritto il tuo codice erano programmatori migliori delle cagate con cui ho dovuto occuparmi :-)
Gordon Thompson

3
  1. C è un linguaggio semplice, C ++ non lo è. Per molte persone, C ++ è semplicemente troppo complicato per padroneggiarlo completamente, vedere http://en.wikipedia.org/wiki/C%2B%2B#Criticism .

  2. A causa della complessità, programmatori diversi di solito padroneggiano solo diversi sottoinsiemi del linguaggio. Rende doloroso leggere il codice di altre persone.

  3. La complessità e le insidie ​​del linguaggio aggiungono troppa distrazione e talvolta danneggiano la produttività. Invece di concentrarmi sul lavoro stesso, mi sono ritrovato spesso a litigare con la lingua stessa. Java / python sono alternative più produttive.

  4. Il debug di un codice C non funzionante è solitamente molto più semplice del debug di un codice C ++ danneggiato.

  5. A differenza di Java / C #, la libreria standard C ++ ottiene poco oltre l'ambito della libreria standard C.

  6. Alcuni programmatori famosi come Linus Torvalds (Linux) e Richard Stallman (Emacs) non amano il C ++.


3
Ho considerato di votare la tua risposta solo fino a quando non ho letto l'argomento n. 6.
fuz

1

La maggior parte dei programmatori dà per scontato che tutti considerino la qualità una priorità assoluta. Non è sempre così. Se sei abituato al C, potrebbe sembrare che C ++ stia facendo troppo per te dietro le quinte. Anche la rigidità del controllo del tipo in C ++ potrebbe sembrare limitante. Molte persone sono disposte a rischiare di introdurre i tipi di bug che il C ++ può aiutare a prevenire per evitare questi "fastidi".


1
Hmm, il motivo per cui sono passato da C a C ++ (molto tempo fa) era per il controllo del tipo più rigoroso. Mi piace che il compilatore trovi i miei errori piuttosto che l'utente che sperimenta un core dump.

1

Ci sono tre ragioni a cui riesco a pensare. Uno è che C è più adatto per i sistemi embedded, a causa delle dimensioni ridotte dei suoi binari e della più ampia disponibilità di compilatori C su qualsiasi sistema. Il secondo è la portabilità: C è un linguaggio più piccolo e il codice ANSI C verrà compilato ovunque. È più facile violare la portabilità in C ++. L'ultima è la lingua stessa. Il C ++ è più difficile ed è decisamente un linguaggio progettato molto male. Le lamentele di Torvalds sono riportate sopra. Puoi anche consultare le risposte alle domande frequenti in C ++ ( http://yosefk.com/c++fqa/ ).


5
E, se sei intelligente, dopo aver esaminato la FQA ti renderai conto che è un lavoro di hacking da parte di qualcuno che non capisce veramente il C ++ ma lo odia comunque.
David Thornley

1

La portabilità può essere un problema. Diversamente dalla risposta di Gordon Carpenter-Thomp, suggerirei che è piuttosto il supporto runtime di diverse versioni di libstdc ++ su diverse versioni di linux / unix. Vedi questo link per una buona discussione su questo. Un piccolo estratto:

Il codice di supporto runtime utilizzato da diverse parti di un'applicazione C ++ deve essere compatibile. Se una parte del programma deve eseguire dynamic_cast o catturare oggetti forniti da un'altra, entrambe le parti devono concordare alcuni dettagli di implementazione: come trovare vtables, come srotolare lo stack e così via.

Per C ++ e pochi altri linguaggi supportati da GCC con caratteristiche simili, tali dettagli sono specificati da un C ++ ABI. Ogni volta che l'ABI utilizzato da GCC cambia, vi ritroverete con librerie incompatibili prodotte dalle diverse versioni di GCC. Lo stesso vale per il C semplice, ma l'ABI C è molto più semplice ed è in circolazione da molto più tempo, quindi è abbastanza stabile.


1

Posso seguire molti suggerimenti qui in entrambe le direzioni. Ma alla fine si tratta di a) comparabile semplice b) comparabile complesso.

Non ho idea se qualcuno abbia "inventato" una sorta di misurazione della complessità del linguaggio.

Su una scala da 0 a 10, probabilmente classificherei C a 2 o 3 mentre C ++ sarebbe tra 8-10. Direi che il C ++ è uno dei linguaggi più complessi ma non conosco, ad esempio, Ada, PL1 o simili, quindi forse non è così complesso rispetto a qualche altro linguaggio.

C ++ eredita tutta la complessità di C quindi non può essere inferiore al livello di complessità di C.

Da parte mia sarei molto più a mio agio nell'usare un linguaggio di scripting e C. Quindi alla fine bisogna rispondere alla seguente domanda. "Di più è sempre meglio?"


1

La cosa più utile che ho trovato in C è la mancanza di spazi dei nomi e sovraccarichi: i nomi di funzioni e simboli sono identificatori univoci. Per trovare i luoghi in cui vengono utilizzati questi simboli puoi semplicementegrep attraverso i file del codice sorgente ei risultati della ricerca mostreranno le posizioni.

È essenziale quando si collega una nuova funzione o componente a un sistema vecchio e aggrovigliato.

Non puoi farlo facilmente in C ++, senza un sofisticato strumento di creazione di grafici di chiamata.


0

La maggior parte delle persone sembra pensare che C e C ++ siano in qualche modo correlati, ma purtroppo si sbagliano. C ++ è un linguaggio completamente diverso da C.

In C ++, pensi in termini di oggetti e di come sono correlati tra loro. In C, pensi in termini di API. È come la differenza tra il giorno e il 17.

Una povera analogia: se qualcuno aggiunge il cinese all'inglese e lo chiama inglese ++, probabilmente non ti sentiresti a tuo agio ad aggiungere una linea cinese alla tua ultima lettera d'amore, perché è molto più facile esprimere amore in questa parte dell'inglese ++.


0

I seguenti sono tutti motivi per cui potrebbe essere utile limitare un progetto a C:

  • compilazione più veloce perché il linguaggio è molto più semplice
  • richiede meno supporto di runtime, rendendolo più adatto agli ambienti di basso livello
  • molto più facile da interfacciare con altre lingue
  • supporta array di dimensioni variabili sullo stack
  • codice assembly più facile da leggere perché non c'è alterazione del nome
  • consente di combinare facilmente il codice prodotto da compilatori diversi poiché è l'interfaccia binaria dell'applicazione standard di fatto
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.