Quais seriam as limitações do C ++ em comparação com a linguagem C? [fechadas]


116

A seguir estão os benefícios do C ++

  • C ++ fornece os recursos específicos sobre os quais eles estão perguntando
  • Seu compilador C é quase certamente um compilador C ++, portanto, não há implicações de custo de software
  • C ++ é tão portátil quanto C
  • O código C ++ pode ser tão eficiente quanto C (ou mais ou menos)

Existem razões concretas e cenários específicos, onde é necessário usar C em vez de C ++?

Referência a esta pergunta: Biblioteca para genéricos em C

Não uma duplicata, porque esta pergunta é sobre as limitações do idioma e não sobre o deve / não deve aprender um idioma em vez de outro.

A postagem de Peter Kirkham foi para mim a mais informativa, principalmente em relação às questões do C99 que eu não havia considerado, então aceitei. Obrigado a todos os outros que participaram.


12
Não importa se esta questão pretende ser argumentativa ou não, ainda é. A escolha do idioma para um projeto é exatamente isso: uma escolha.
Bombe

7
@bombe não devemos discutir como fazer escolhas informadas?



10
Não é irônico quando você aconselha os programadores C a mudarem para C ++ que eles são tão receptivos à sua ideia, como você seria, se um programador C dissesse que você deveria abandonar C ++ e mudar para C?
Warren P

Respostas:


136

Isso é solicitado por uma resposta que dei a uma pergunta atual que pergunta sobre uma biblioteca de genéricos para C - o questionador afirma especificamente que não deseja usar C ++.

C é uma linguagem de programação completa. C não é um subconjunto arbitrário de C ++. C não é um subconjunto de C ++.

Este é C válido:

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

Para fazer a compilação como C ++, você deve escrever:

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

que não é mais válido C. (você poderia usar o elenco de estilo C, caso em que seria compilado em C, mas seria evitado pela maioria dos padrões de codificação C ++ e também por muitos programadores C; testemunhe os comentários "não elenco malloc" em todo o Stack Overflow) .


Eles não são a mesma linguagem e, se você tiver um projeto existente em C, não deseja reescrevê-lo em uma linguagem diferente apenas para usar uma biblioteca. Você prefere usar bibliotecas com as quais possa interagir na linguagem em que está trabalhando. (Em alguns casos, isso é possível com algumas extern "C"funções de invólucro, dependendo de como é o modelo / inline uma biblioteca C ++.)

Pegando o primeiro arquivo C em um projeto no qual estou trabalhando, isso é o que acontece se você apenas trocar gcc std=c99por 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

No total, 69 linhas de erros, quatro dos quais são conversões inválidas, mas principalmente para recursos que existem no C99, mas não no C ++.

Não é como se eu estivesse usando esses recursos para me divertir. Seria um trabalho significativo transferi-lo para um idioma diferente.

Portanto, é totalmente errado sugerir que

[a] O compilador C quase certamente é um compilador C ++, portanto, não há implicações de custo de software

Freqüentemente, há implicações de custo significativas na portabilidade do código C existente para o subconjunto procedimental do C ++.

Portanto, sugerir 'usar a classe C ++ std :: queue' como uma resposta à pergunta em busca de uma implementação de biblioteca de uma fila em C é mais rápido do que sugerir 'usar C objetivo' e 'chamar a classe Java java.util.Queue usando JNI' ou 'chamar a biblioteca CPython' - Objective C realmente é um superconjunto apropriado de C (incluindo C99), e as bibliotecas Java e CPython podem ser chamadas diretamente de C sem ter que portar código não relacionado para a linguagem C ++.

Claro que você pode fornecer uma fachada C para a biblioteca C ++, mas uma vez que você está fazendo isso, C ++ não é diferente de Java ou Python.


21
Sim. O elenco de estilo C é bastante comum quando você usa malloc. Ao usar malloc, você deve permanecer dentro do subconjunto c. Se você quiser programar no estilo C ++, deve usar o operador new, não static_cast + malloc.
Suma,

33
Dizer que C não é um subconjunto de C ++ é incrivelmente pedante. Claro, você poderia dizer que qualquer struct com um membro chamado "class" não compilará, mas na verdade são apenas pequenas modificações que são necessárias, e a maioria dos compiladores tem opções para adicionar os poucos recursos somente C ao C ++.
Kaz Dragon de

27
no que diz respeito ao seu exemplo malloc, adicionar um elenco não seria apenas evitado por programadores C ++, mas também (especialmente) por programadores C. Existem boas razões para omitir o elenco no código C. Não é necessário e adicioná-lo pode ocultar erros. Então sim, trate-os como duas línguas distintas. +1 :)
jalf

26
@BlueRaja Imagine se Guido tivesse decidido não adicionar objetos à sua linguagem de script e dois grupos tivessem criado forks mutuamente incompatíveis de Python para adicionar objetos, um com um modelo de objeto baseado em Smalltalk, o outro com um sistema de classes baseado em Simula. Então Guido continuou a melhorar o Python focando seu uso principal. Isso é mais próximo da situação C / Objective C / C ++.
Pete Kirkham

11
@BlueRaja: São duas linguagens distintas que compartilham um núcleo comum bastante grande. Se você programar nesse núcleo comum, acabará fazendo coisas que não são um bom código em nenhuma das linguagens. Escolha um idioma para escrever qualquer programa e torne-o bom nesse idioma.
David Thornley

115

Sei que não é uma resposta profissional nem específica, mas para mim é simplesmente porque gosto muito de C. C é pequeno e simples e posso caber toda a linguagem em meu cérebro, C ++ para mim sempre pareceu uma grande bagunça com todos os tipos de camadas, tenho dificuldade em grocar. Devido a isso, descubro que sempre que escrevo C ++ acabo gastando muito mais tempo depurando e batendo minha cabeça contra superfícies rígidas do que quando codifico C. Mais uma vez, percebo que muito disso é em grande parte resultado de minha própria 'ignorância'.

Se eu puder escolher, escreverei todas as coisas de alto nível, como a interface e a interação do banco de dados em python (ou possivelmente C #) e todas as coisas que precisam ser rápidas em C. Para mim, isso me dá o melhor de todos os mundos. Escrever tudo em C ++ é como obter o pior de todos os mundos.

Edit: gostaria de acrescentar que acho que C com alguns recursos C ++ é em grande parte uma má ideia se você vai ser várias pessoas trabalhando em um projeto ou se a manutenção é prioridade. Haverá discordância sobre o que constitui 'alguns' e quais bits devem ser feitos em C e quais bits em C ++ levam eventualmente a uma base de código muito esquizofrênica.


24
Usei C ++ por vários anos e ainda gastei 50% do meu tempo refatorando código para ficar "C ++ correto". É um pesadelo, como você diz.
Kai

12
Você sempre pode fazer certo da primeira vez. Adicionar const não é difícil.
GManNickG

14
Usei C ++ por dez anos e voltar para C (para sistemas embarcados, no meu caso) foi a melhor coisa que já fiz.
Warren P

Eu amo essa resposta. Você acertou meus sentimentos também. Tive anos de trabalho como dev C ++, meu trabalho diário ainda é C ++. Mas isso não significa que eu goste da linguagem, vejo beleza em C.
Matt Joiner

10
+1, Devido a isso eu acho que sempre que eu escrever C ++ eu acabar gastando muito mais tempo de depuração e batendo a cabeça contra superfícies duras do que quando eu código C . Não posso concordar mais com você. A melhor resposta. :)
ApprenticeHacker

58

C ++ simplesmente não tem suporte em alguns ambientes do mundo real, como sistemas embarcados de baixo nível. E há uma boa razão para isso: C facilmente bom o suficiente para essas coisas, então por que usar algo maior?


2
Certo. Já vi compiladores c para micro controladores de 8 bits.
dmckee --- ex-moderador gatinho

6
claro. A maioria, senão todos os chips de 8 bits, tem compiladores C atualmente.
Eli Bendersky


+1 esta é a resposta correta. Os compiladores C ++ são muito mais difíceis de escrever do que os compiladores C, em grande parte devido às complexidades da herança (múltipla).
BlueRaja - Danny Pflughoeft

9
@BlueRaja: comparado aos modelos ... herança múltipla pode não ser o verdadeiro impedimento aqui. Afinal, os modelos constituem uma linguagem própria e completa.
Matthieu M.

49

Eu odeio programar em C ++.


6
Lol eu gosto desse
Tamas Czinege

30
Muito convincente! Estou pensando em mudar para Python com base em seu argumento.
Jimmy J

8
Talvez não seja convincente, mas é o verdadeiro motivo.
Georg Schölly

@Jimmy J: Python é incrível. É o melhor do Unix, C e todos os seus recursos de linguagem "modernos" feitos corretamente. Se você tiver problemas de desempenho, o Python deseja que você entre em C e o faz facilmente.
Matt Joiner de

2
@Georg: Admito que nunca dei uma olhada, estou tão impressionado com o Python.
Matt Joiner de

38

Alguns motivos podem ser:

  • Falta de suporte - Nem todo compilador C também é um compilador C ++. Nem todos os compiladores são particularmente compatíveis com o padrão, mesmo que afirmem oferecer suporte a C ++. E alguns compiladores C ++ geram código irremediavelmente inchado e ineficiente. Alguns compiladores têm implementações terríveis da biblioteca padrão. O desenvolvimento no modo kernel geralmente torna o uso da biblioteca padrão C ++ impossível, bem como alguns recursos de linguagem. Você ainda pode escrever código C ++ se se ater ao núcleo da linguagem, mas pode ser mais simples mudar para C.
  • Familiaridade. C ++ é uma linguagem complexa. É mais fácil ensinar C a alguém do que C ++, e é mais fácil encontrar um bom programador C do que um bom programador C ++. (a palavra-chave aqui é "boa". Existem muitos programadores C ++, mas a maioria deles não aprendeu a linguagem corretamente)
  • Curva de aprendizado - Como acima, ensinar C ++ a alguém é uma tarefa enorme. Se você está escrevendo um aplicativo que precisa ser mantido por outros no futuro, e esses outros podem não ser programadores C ++, escrevê-lo em C o torna muito mais fácil de lidar.

Ainda prefiro escrever em C ++ quando posso me safar e, no geral, acho que os benefícios superam as desvantagens. Mas também posso ver o argumento para usar C em alguns casos.


4
Eu acrescentaria que o código C compila muito mais rápido do que C ++. Um grande projeto em nossa empresa (mais de um milhão de linhas) compila menos de 30 segundos.
Calmarius,

31

Existem muitos argumentos sobre programação embarcada, desempenho e outras coisas, eu não os compro. C ++ se compara facilmente a C nessas áreas.Contudo:

Recentemente, depois de programar em C ++ por mais de 15 anos, redescobri minhas raízes em C. Devo dizer que embora existam bons recursos em C ++ que tornam a vida mais fácil, também há uma série de armadilhas e uma espécie de "sempre-existe-uma-maneira-melhor-de-fazer as coisas. Você nunca fica realmente muito feliz com a solução que deu. (Não me entenda mal, isso pode ser uma coisa boa, mas principalmente não).

C ++ oferece tiroteio infinito. O que pode ser indiscutivelmente bom, mas de alguma forma você sempre acaba usando muito disso. Isso significa que você está disfarçando suas soluções com camadas "bonitas" e "bonitas" de abstrações, generalidades, etc.

O que descobri voltando para C foi que era realmente divertido programar novamente. Tendo gasto tanto tempo modelando e pensando sobre como usar melhor a herança, descobri que programar em C na verdade torna meu código-fonte menor e mais legível. É claro que isso depende do seu nível de autodisciplina. Mas é muito fácil colocar muitas abstrações em código direto, o que nunca é realmente necessário.


8
Sem ofensa, mas também pode depender do que você pensa que é C ++. Herança é algo que associo mais com Java do que C ++, e se você tratar C ++ estritamente como uma linguagem OOP à la Java (C com classes), então eu concordo com você. Se você ficar com um sabor mais moderno de C ++, acho que é mais divertido do que C
jalf

11
Mais uma vez, porém, não penso em C ++ como uma linguagem OO e não deve ser tratada como tal. Acho que a programação genérica é uma característica muito mais forte do C ++. A maior parte do código C ++ que vejo não se esforça muito para ser "OO" ou contém código desnecessário. Muitas vezes é mais enxuto do que o código C equivalente
jalf

3
@jalf: Outra coisa que acho que pode se tornar uma distração do tipo "há sempre um jeito melhor" em C ++ é generalizar as coisas com modelos. "Talvez devêssemos deixar o usuário desta classe decidir que tipo de inteiro subjacente usar?" Mas você provavelmente não precisa disso, e em C você não se importaria. E às vezes me pego pensando: "Devemos realmente fornecer uma interface de iteração direta para esta classe", quando em C você apenas exporia um ponteiro para o primeiro elemento e uma contagem, ou (o máximo da fantasia!) Uma função tomando um ponteiro de função de retorno de chamada.
j_random_hacker

2
Acho que dar um passo para trás ao codificar em C ++ ajuda. Decida o objetivo e escreva sobre ele (estilo C). Considere os ismos C ++ conforme sua utilidade se tornar aparente.
Matt Joiner de

2
infinite gunfire, ooh sim, é verdade. Nossos pés literalmente tremem :)
quetzalcoatl

27

C tem a principal vantagem de que você pode ver o que realmente está acontecendo quando você olha para algum trecho de código (sim, pré-processador: compile com -E e então você verá). Algo que muitas vezes não é verdade quando você olha para algum código C ++. Lá você tem construtores e destruidores que são chamados implicitamente com base no escopo ou devido a atribuições, você tem sobrecarga de operador que pode ter um comportamento surpreendente, mesmo quando não é mal utilizado. Admito que sou um maníaco por controle, mas cheguei à conclusão de que esse não é um hábito tão ruim para um desenvolvedor de software que deseja escrever um software confiável. Só quero ter uma chance justa de dizer que meu software faz exatamente o que deve fazer e não tem uma sensação ruim no estômago ao mesmo tempo, porque sei que ainda pode haver tantos bugs nele que eu não faria

C ++ também possui modelos. Eu os odeio e amo, mas se alguém disser que os compreende perfeitamente, eu o chamo de mentiroso! Isso inclui os redatores do compilador, bem como as pessoas envolvidas na definição do padrão (o que se torna óbvio quando você tenta lê-lo). Há tantos casos extremos absurdamente enganosos envolvidos que simplesmente não é possível considerá-los todos enquanto você escreve o código real. Eu amo os modelos C ++ por seu poder absoluto. É realmente incrível o que você pode fazer com eles, mas eles também podem levar aos erros mais estranhos e difíceis de encontrar que alguém pode (não) imaginar. E esses erros realmente acontecem e nem mesmo raramente. Ler sobre as regras envolvidas para resolver modelos no ARM C ++ quase fez minha cabeça explodir. E me dá a sensação ruim de perda de tempo tendo que ler mensagens de erro do compilador com vários 1000 caracteres, para as quais eu preciso de 10 minutos ou mais para entender o que o compilador realmente quer de mim. No código C ++ (biblioteca) típico, você também costuma encontrar muitos códigos em arquivos de cabeçalho para possibilitar certos modelos, o que, por sua vez, torna os ciclos de compilação / execução extremamente lentos, mesmo em máquinas rápidas e requer a recompilação de grandes partes do código quando você altera algo há.

C ++ também tem a armadilha const. Você evita const para todos, exceto os casos de uso mais triviais, ou mais cedo ou mais tarde terá que descartá-lo ou refatorar grandes partes da base de código quando ela evoluir, especialmente quando você está prestes a desenvolver um design OO agradável e flexível.

C ++ tem uma digitação mais forte do que C, o que é ótimo, mas às vezes sinto que estou alimentando um Tamagotchi quando tento compilar o código C ++. Uma grande parte dos avisos e erros que normalmente recebo dele não são realmente eu fazendo algo que não funcionaria, mas apenas coisas que o compilador não gosta que eu faça desta forma ou não sem lançar ou colocar algumas palavras-chave extras aqui e há.

Essas são apenas algumas das razões pelas quais não gosto de C ++ para software que escrevo sozinho apenas usando algumas bibliotecas externas supostamente robustas. O verdadeiro horror começa quando você escreve código em equipes com outras pessoas. Quase não importa se eles são hackers de C ++ muito espertos ou iniciantes ingênuos. Todo mundo comete erros, mas C ++ torna deliberadamente difícil encontrá-los e ainda mais difícil identificá-los antes que aconteçam.

Com C ++, você fica simplesmente perdido sem usar um depurador o tempo todo, mas eu gosto de poder verificar a exatidão do meu código na minha cabeça e não ter que depender de um depurador para encontrar meu código rodando em caminhos que eu nunca teria antecipado. Na verdade, tento executar todo o meu código na minha cabeça e tento pegar todos os ramos que ele tem, mesmo em sub-rotinas etc. e usar um depurador apenas ocasionalmente para ver como ele funciona bem em todos os lugares aconchegantes que preparei para isso. Escrever e executar tantos casos de teste que todos os caminhos de código foram usados ​​em todas as combinações com todos os tipos de dados de entrada estranhos é simplesmente impossível. Portanto, você pode não saber dos bugs nos programas C ++, mas isso não significa que eles não existam. Quanto maior se torna um projeto C ++, menor fica minha confiança de que ele não terá muitos bugs não detectados, mesmo se funcionar perfeitamente com todos os dados de teste que temos em mãos. Eventualmente, eu o destruo e começo de novo com alguma outra linguagem ou combinação de outras línguas.

Eu poderia continuar, mas acho que deixei meu ponto claro agora. Tudo isso me fez sentir improdutivo quando programo em C ++ e me fez perder a confiança na exatidão do meu próprio código, o que significa que não o usarei mais, enquanto ainda uso e confio no código C que escrevi mais de 20 anos atrás. Talvez seja simplesmente porque eu não sou um bom programador C ++, ou talvez ser muito bom em C e outras linguagens me permite reconhecer o quão lamer eu realmente sou quando se trata de C ++, e que nunca serei capaz de compreendê-lo totalmente .

A vida é curta...


2
1, não poderia concordar mais.
missingfaktor,

2
Isso soa notavelmente paralelo ao argumento de Linus. (Menos de um contexto de objeto = mais fácil de entender.)
Warren P

20

Em um ambiente embarcado de baixo nível, alguns dos "engenheiros de software" terão formação em EE e mal dominarão C. C ++ é mais complexo e alguns desses caras simplesmente têm medo de aprender uma nova linguagem. Assim, C é usado como o menor denominador comum. (Antes de sugerir se livrar desses caras, eles são pelo menos tão importantes quanto os especialistas em ciência da computação que não entendem o analógico hardcore.)

Falando por experiência própria em ter herdado e mantido ambos: um design horrível em C é difícil de entender, desenrolar e refatorar em algo utilizável.

Um design horrível em C ++ é infinitamente pior, já que camadas aleatórias de abstração fazem seu cérebro girar rapidamente em torno da base de código tentando descobrir qual código será executado em qual circunstância.

Se tiver que trabalhar com engenheiros que sei que não produzirão grandes projetos, prefiro muito mais o primeiro do que o segundo.


Amém, irmão. Tendo trabalhado com código-fonte C produzido por engenheiros de hardware, estremeço ao pensar no que enfrentaria se eles tivessem feito isso em C ++.
Richard Chambers,

19

Não vejo outra razão além da antipatia pessoal, mesmo para a programação de sistemas embarcados e coisas semelhantes. Em C ++, você paga despesas indiretas apenas pelos recursos que usa. Você pode usar o subconjunto C do C ++ em algumas situações específicas em que a sobrecarga do C ++ é muito alta para você. Dito isso, acho que alguns programadores de C superestimam a sobrecarga de algumas construções de C ++. Deixe-me listar alguns exemplos:

  • Classes e funções-membro têm sobrecarga zero em comparação com funções normais (a menos que você use funções virtuais, caso em que não há sobrecarga em comparação com o uso de ponteiros de funções)
  • Os modelos têm muito pouca sobrecarga (na maioria das vezes, nenhuma sobrecarga)

Um motivo válido seria quando você está programando para uma plataforma que não tem um compilador C ++ decente (nenhum compilador C ++ ou existe um compilador, mas está implementado de maneira inadequada e impõe uma sobrecarga desnecessária para alguns recursos C ++).


3
Uma classe com funções virtuais tem mais sobrecarga: cada instância precisa carregar um campo extra para identificar o tipo.
bstpierre

6
Mais sobrecarga do que o quê? O tipo é transportado no vtbl. Se você implementar um mecanismo semelhante usando ponteiros de função, precisará de pelo menos um ponteiro (ou índice, ou qualquer outro) para selecionar o ponteiro de função que deseja usar.
Suma,

3
bstpierre: Acho que o que Suma está dizendo é: que não há mais sobrecarga do que implementar o recurso manualmente em C.
Martin York

2
Um ponteiro para as classes vtable é armazenado em cada instância da classe.
tstenner de

5
Há uma sobrecarga, mas o que quero dizer é que se você quiser qualquer resolução de tipo dinâmico, precisa de algum armazenamento para identificar o tipo, mesmo em C. Se você não quiser os tipos dinâmicos, não precisa pagar pela sobrecarga ( não use funções virtuais se não precisar delas).
Suma,

13

Por que limitar a fala em inglês? Talvez você seja um autor mais criativo em sérvio.

Esse é o mesmo argumento, com falácias óbvias. Se você tem uma tarefa e suas ferramentas confortáveis ​​resolvem a tarefa com eficiência, você provavelmente usará suas ferramentas confortáveis ​​por um bom motivo.


3
Se eu falasse inglês fluente e sérvio fluente, tenho certeza que seria mais criativo. Você discorda?

2
@Neil de fato, mas o esforço necessário para aprender sérvio pode não ser justificado para resolver meu atual bloqueio de criatividade.
slim,

2
Acho que Arno está destacando o fato de que você não está escrevendo para a CPU, está escrevendo para seus colegas de trabalho lerem, e para suas outras bibliotecas vincularem, e assim por diante. Afinal, se eu quisesse apenas expressividade e velocidade, escreveria em OCaml.
Ken

10

C ++ tem uma curva de aprendizado muito mais longa. C tem apenas algumas construções de que você precisa estar ciente e então você pode começar a codificar um software poderoso. Em C ++ você precisa aprender a base C, então o OO e programação genérica, exceção, etc. E depois de um tempo você pode saber a maioria dos recursos e você provavelmente pode usá-los, mas você ainda não sabe como o compilador irá traduzi-los, que overhead implícito eles têm ou não. Isso leva muito tempo e energia.

Para um projeto profissional, esse argumento pode não contar, porque você pode empregar pessoas que já conhecem C ++ muito bem. Mas em projetos de código aberto, onde C ainda é amplamente usado, as pessoas escolhem a linguagem que gostam e são capazes de usar. Considere que nem todo programador de sistema operacional é um programador profissional.


1
Erm ... não? Você aprende a base C (possivelmente com exceção dos arrays e do tratamento de strings no estilo C abandonados em favor de <vector> e <string>) e segue em frente. Você pode pegar todo o resto à medida que avança. Você não precisa saber nada sobre OO, GP ou exceções para começar com C ++ ...
DevSolar

4
C pode ser "menor", mas a longo prazo não é mais fácil de usar. Gerenciamento de memória manual? Não, obrigado.
Jimmy J

7
Não existe gerenciamento automático de memória em C ++.
Warren P

3
C ++ não resolve o problema de gerenciamento de memória. Bem quando você pensava que tinha domínio sobre os ponteiros, C ++ vai e adiciona um modelo de exceção terrível. Venha para a terra C99, exceto para estruturas de dados, tenho quase certeza de que mal toquei em malloc. Mesmo assim, posso "encapsular" um punhado de chamadas malloc. É quase a mesma história em C ++ (gerenciamento de memória implícita, apenas é feito no heap em vez de na pilha), apenas com todo o jazz do ponteiro inteligente.
Matt Joiner de

1
@ereOn: É verdade, o comentário que escrevi há 3 anos não se sustenta mais. :)
Matt Joiner

10

Eu gostaria de acompanhar a resposta de Dan Olson. Eu acredito que as pessoas temem os recursos potencialmente perigosos e contraproducentes do C ++, e com razão. Mas, ao contrário do que Dan diz, não acho que simplesmente decidir sobre um padrão de codificação seja eficaz, por dois motivos:

  1. Os padrões de codificação podem ser difíceis de aplicar estritamente
  2. Pode ser muito difícil encontrar um bom.

Acho que a segunda razão aqui é muito mais importante do que a primeira, porque decidir sobre um padrão de codificação pode facilmente se tornar uma questão política e estar sujeita a revisão posteriormente. Considere o seguinte caso simplificado:

  1. Você tem permissão para usar contêineres stl, mas não para usar modelos em qualquer um de seu próprio código.
  2. As pessoas começam a reclamar que seriam mais produtivas se apenas pudessem codificar esta ou aquela classe de modelo.
  3. O padrão de codificação é revisado para permitir isso.
  4. Deslize um pouco para um padrão de codificação excessivamente complicado que ninguém segue e use exatamente o tipo de código perigoso que o padrão deveria evitar, combinado com o excesso de burocracia em torno do padrão.

(A alternativa de que o padrão não seja revisado na etapa 3 é empiricamente muito improvável para ser considerada e não seria muito melhor de qualquer maneira.)

Embora eu costumava usar C ++ para quase tudo há alguns anos, estou começando a sentir fortemente que C é preferível em tarefas de baixo nível que precisam ser manipuladas por C ou C ++ e todo o resto deve ser feito em algum outro linguagem inteiramente. (As únicas exceções possíveis são alguns domínios de problemas específicos de alto desempenho, wrt. Blitz ++ )


10

Eu uso C, ou pelo menos exporto uma interface C quando escrevo o código da biblioteca.

Eu não quero aborrecimentos mal definidos de ABI.


Mesmo. C estrito apenas em interfaces. A última coisa que quero é a estrutura de objetos ridícula de outra pessoa empurrada para mim.
Matt Joiner de

9

Nunca vi nenhum argumento para usar C sobre C ++ que considerasse convincente. Acho que a maioria das pessoas tem medo de certos recursos que o C ++ oferece, muitas vezes com razão. No entanto, isso não me convence, porque é possível impor o uso ou não de determinados recursos por meio de padrões de codificação. Mesmo em C, há muitas coisas que você deseja evitar. Descartar C ++ inteiramente é essencialmente dizer que ele não oferece benefícios tangíveis em relação ao C que ajudariam a escrever um código melhor, que é uma visão que considero bastante ignorante.

Além disso, as pessoas sempre parecem levantar a situação de plataformas onde não existe um compilador C ++. Certamente C seria apropriado aqui, mas acho que você teria dificuldade em encontrar uma plataforma como essa hoje em dia.


3
Concordado, os discursos "C é melhor que C ++" nunca resistem a um exame minucioso.
Jimmy J de

6
Eu acredito que C ++ me oferece MUITO POUCO benefício e me CUSTA uma enorme quantidade de complexidade acidental. Acredito que seriam necessárias cerca de 1.500 páginas de livros de C ++ e dez anos de esforço para me tornar tão proficiente em C ++ quanto sou atualmente em C, Pascal, Python e Objective-C. Cada uma das linguagens acima é cerca de 20 vezes mais ortogonal, compacta e mentalmente conveniente de usar, para não mencionar mais poderosa, nos ambientes onde eu as uso. Simplesmente NÃO há usos racionalmente justificáveis ​​para C ++ em meus ambientes de desenvolvimento usuais.
Warren P

@ Warren Você só paga pelo que usa, como qualquer idioma. Se você não é capaz de decidir como codificar sabiamente em C ++, isso depende de você, não da linguagem.
Dan Olson

2
Não tão. Se você for o único desenvolvedor em um projeto, pode ser que seja. Mas assim que tivermos dois desenvolvedores, teremos batalhas. O que? Você insiste em containers IoC, embora eu prefira alguma outra maneira de fazer delegados ... Você gosta de três níveis de modelos aninhados e eu prefiro zero modelos. Uma bagunça.
Warren P

Eu sei que este post tem 10 anos, mas é realmente justo comparar C e C ++ mais? Ambos são linguagens separadas e divergentes (desde C99) e ambos têm suas vantagens e desvantagens que cada um cobre. C ++ é difícil de depurar e manter? A explicitação do C permite que você depure melhor. C não tem genéricos? C ++ tem genéricos! Neste momento, nenhum idioma é melhor do que o outro.
Nergal de

9

Um ponto que ainda não vi levantado, que considero o mais importante:

A maioria das bibliotecas que uso diariamente são bibliotecas C com vínculos para Python, Ruby, Perl, Java, etc. Pelo que tenho visto, é muito mais fácil agrupar bibliotecas C com 19 vínculos de linguagem diferentes do que agrupar bibliotecas C ++.

Por exemplo, eu aprendi Cairo uma vez e, desde então, usei-o em 3 ou 4 idiomas diferentes. Grande vitória! Prefiro escrever um programa que possa ser usado novamente no futuro, e escrever um que possa ser facilmente adotado para outras linguagens de programação é um caso extremo disso.

Eu sei que é possível ligar bibliotecas C ++, mas AFAICT não é a mesma coisa. Eu usei Qt (v3 e v4) em outras linguagens e não é nem de perto tão bom de usar: eles parecem escrever C ++ em alguma outra linguagem, não como bibliotecas nativas. (Você deve passar sigs do método C ++ como strings!)

C ++ é provavelmente uma linguagem melhor se você estiver escrevendo uma função para ser usada uma vez, ou se você achar que todo o mundo é C ++. C parece ser uma linguagem mais fácil se você estiver projetando para portabilidade de linguagem desde o início.


O método "passe métodos como strings!" coisa é um defeito do Qt, não C ++. Você poderia realmente ter o mesmo mecanismo estúpido com uma estrutura C que gostaria. Até mesmo os caras do Qt concordam que fazer isso foi um erro. Simplesmente não havia alternativa melhor em sua mente no momento e era tarde demais para mudar de volta quando perceberam.
ereOn

7

O desenvolvimento do kernel do Windows não suporta c ++ (infelizmente).


Como é isso? Por quê? O binário produzido a partir de um compilador C ++ é diferente de um compilador C? O desenvolvimento de drivers não está simplesmente aderindo às APIs?
Dave Van den Eynde

4
Porque muitos recursos C ++ requerem suporte de tempo de execução que pode não ser trivial para implementar no modo kernel. Por um lado, diferentes funções de alocação de memória são usadas, portanto, partes da biblioteca padrão teriam que ser substituídas. As exceções geralmente são ruins também.
jalf

3
Acrescentarei que Linux Torvalds felizmente incendiou qualquer chance de C ++ no Linux por mais razões do que exceções. Existem alguns sistemas operacionais em outras linguagens: Java, C ++, assembler. Apenas os montadores sobreviveram com uso razoável.
Matt Joiner de


Notou que é para o Visual Studio 2015?
LegendLength

6

Você pode ler um discurso divertido sobre por que Linus Torvalds favorece C aqui


6
É mais um discurso meio coerente contra o design orientado a objetos do que um discurso contra C ++.
Dan Olson,

16
O Sr. Torvalds tem uma longa lista de coisas que ele não gosta, C ++, emacs, Subversion, OO para mencionar alguns. Às vezes, alguém gostaria que ele fechasse os lábios um pouco mais

11
Linus gosta de reclamar e tentar provocar e incomodar as pessoas. Infelizmente, ele não se preocupou em aprender C ++ antes de declarar que é uma merda. Infelizmente, seus seguidores acreditam que tudo o que ele diz deve ser verdade.
jalf

9
O link era mais para entretenimento do que educação
Paul Dixon

6
Prova de que até gênios às vezes podem ser idiotas.
Kaz Dragon,

5

O código nativo em um mac é objetivo-c. O código nativo em um PC é c (window.h) ou c ++ (mfc). Ambos os ambientes permitirão que você use c com poucas ou nenhuma alteração. Quando quero que uma biblioteca de código seja multiplataforma, ansi c parece uma boa escolha.


4

Posso pensar em vários motivos.

Pode não haver um compilador C ++ satisfatório. C ++ é uma linguagem muito maior, e executei compiladores C em sistemas que não seriam capazes de lidar com o C ++ moderno.

O questionador, ou as pessoas com quem ele trabalha, podem estar familiarizados com C, mas não com C ++.

O projeto pode estar em C. Embora seja possível adicionar alguns recursos de C ++ ao C, isso pode facilmente levar a uma bagunça impossível de manter. Eu sugiro escolher um idioma ou outro (geralmente C ++, quando prático).

O questionador pode ter uma visão obsoleta da curva de aprendizado do C ++. (Quando abordado corretamente, é mais fácil do que C. A maioria dos livros introdutórios que vi não aborda isso corretamente.)

Lembre-se de que C e C ++ são duas linguagens diferentes e estão ficando mais diferentes com o tempo. Codificar em ambos ao mesmo tempo é uma má ideia, e usar um subconjunto do C ++ como o C perde a maioria das vantagens do C ++.


3

Se você trabalha em um ambiente com duas linguagens, pode usar C para algumas funções críticas de desempenho de baixo nível e uma linguagem mais funcional / de alto nível como C # / Java para a lógica de negócios. Se o código C ++ for usado para essas funções, os C-Wrappers serão necessários para o código JNI / não gerenciado e isso torna as coisas mais complexas do que apenas usar C.


3

Eu uso C ++ com programação C por dois motivos:

  • vectore stringtirar o gerenciamento de memória do array longe de mim
  • verificação de tipo e conversões estritas para avisar e / ou detectar todos os incômodos que eu perderia de outra forma.

Portanto, é C realmente pegando emprestado alguns C ++, mas usando o compilador C ++ o máximo que posso. Como outra pessoa disse nas respostas, acho que agora estou pegando mais C ++ dessa forma e onde C seria muito envolvente, eu uso C ++. Monitorar / bloquear usando RAII é um desses que usei recentemente ao lidar com programas multi-threaded e outra construção semelhante para abrir / fechar arquivos.


3

Acho que C é mais portátil. Eu fiz alguns trabalhos cerca de 5 anos atrás, portando código para muitos sabores de Unix (AIX, Irix, HPUX, Linux). O código C foi fácil de transportar, mas tivemos vários problemas ao transportar parte do código C ++. Talvez fossem apenas ambientes de desenvolvimento imaturos, mas eu preferia usar C em vez de C ++ por este motivo ...


1
Quinze anos atrás, fui o desenvolvedor principal de um projeto C ++ voltado para HPUX, AIX e Solaris. Tivemos poucos problemas de portabilidade C ++ - quase todos os problemas que tínhamos eram com incompatibilidades de chamada de sistema C.

1
Menos de dez anos atrás, eu estava em um projeto usando HPUX, Solaris e Tru64, usando os compiladores tradicionais. Nossos nightlies nunca construíram. Quando adicionamos o AIX, decidimos mudar para o C ++ padrão.
David Thornley,

Talvez as pessoas que escreveram seu código fossem melhores programadores do que a porcaria com a qual eu tive que lidar :-)
Gordon Thompson

3
  1. C é uma linguagem simples, C ++ não. Para muitas pessoas, C ++ é simplesmente muito complicado para dominar totalmente, consulte http://en.wikipedia.org/wiki/C%2B%2B#Criticism .

  2. Por causa da complexidade, diferentes programadores geralmente dominam apenas diferentes subconjuntos da linguagem. Isso torna a leitura do código de outras pessoas dolorosa.

  3. A complexidade e as armadilhas da linguagem adicionam muita distração e, às vezes, prejudicam a produtividade. Em vez de me concentrar no trabalho em si, muitas vezes me peguei lutando com a própria linguagem. Java / python são alternativas mais produtivas.

  4. A depuração de um código C quebrado geralmente é muito mais simples do que depurar um código C ++ quebrado.

  5. Ao contrário do Java / C #, a biblioteca padrão C ++ alcança pouco além do escopo da biblioteca padrão C.

  6. Alguns programadores famosos como Linus Torvalds (Linux) e Richard Stallman (Emacs) não gostam de C ++.


3
Considerei votar sua resposta apenas até ler o argumento nº 6.
fuz

1

A maioria dos programadores tem como certo que todos consideram a qualidade uma alta prioridade. Nem sempre é o caso. Se você está acostumado com C, C ++ pode parecer que está fazendo muito por você nos bastidores. A rigidez da verificação de tipo em C ++ também pode parecer restritiva. Muitas pessoas estão dispostas a arriscar introduzir os tipos de bugs que o C ++ pode ajudar a prevenir para evitar esses "incômodos".


1
Hmm, a razão pela qual mudei de C para C ++ (há muito tempo) foi para a verificação de tipo mais rigorosa. Gosto que o compilador encontre meus erros, em vez de que o usuário experimente um despejo de memória.

1

Posso pensar em três razões. Uma é que C é mais adequado para sistemas embarcados, devido ao pequeno tamanho de seus binários e à maior disponibilidade de compiladores C em qualquer sistema. A segunda é a portabilidade: C é uma linguagem menor e o código ANSI C compilará em qualquer lugar. É mais fácil quebrar a portabilidade em C ++. O último é a própria linguagem. C ++ é mais difícil e definitivamente é uma linguagem muito mal projetada. As queixas de Torvalds são relatadas acima. Você também pode consultar as Respostas Frequentemente Questionadas sobre C ++ ( http://yosefk.com/c++fqa/ ).


5
E, se você for inteligente, depois de olhar para o FQA, você perceberá que é um trabalho de hack, feito por alguém que não entende C ++, mas odeia mesmo assim.
David Thornley,

1

A portabilidade pode ser um problema. Diferente da resposta de Gordon Carpenter-Thomp, eu sugeriria que é mais o suporte em tempo de execução de diferentes versões de libstdc ++ em diferentes versões de linux / unix. Veja este link para uma boa discussão sobre isso. Um pequeno trecho:

O código de suporte de tempo de execução usado por diferentes partes de um aplicativo C ++ precisa ser compatível. Se uma parte do programa precisar dynamic_cast ou capturar objetos fornecidos por outra, ambas as partes devem concordar em certos detalhes de implementação: como encontrar vtables, como desfazer a pilha e assim por diante.

Para C ++ e algumas outras linguagens suportadas pelo GCC com recursos semelhantes, tais detalhes são especificados por uma ABI C ++. Sempre que a ABI usada pelo GCC muda, você acaba com bibliotecas incompatíveis produzidas pelas diferentes versões do GCC. O mesmo é verdadeiro para o C simples, mas o C ABI é muito mais simples e existe há muito mais tempo, então é bastante estável.


1

Posso seguir muitas sugestões aqui em ambas as direções. Mas no final tudo se resume a a) simples comparável b) complexo comparável.

Não tenho ideia se alguém "inventou" uma espécie de medição da complexidade da linguagem.

Em uma escala de 0 a 10, eu provavelmente classificaria C como 2 ou 3, enquanto C ++ estaria entre 8-10. Eu diria que C ++ é uma das linguagens mais complexas, mas eu não sei, por exemplo, Ada, PL1 ou semelhantes, então talvez não seja tão complexa em comparação com alguma outra linguagem.

C ++ herda toda a complexidade de C, portanto, não pode estar abaixo do nível de complexidade de C.

Eu, de minha parte, ficaria muito mais confortável usando alguma linguagem de script e C. Portanto, no final, é necessário responder à seguinte pergunta. "É mais sempre melhor?"


1

A coisa mais útil que encontrei em C é a falta de namespaces e sobrecargas: nomes de função e símbolo são identificadores exclusivos. Para encontrar os locais onde esses símbolos são usados, basta grepacessar os arquivos de código-fonte e os resultados da pesquisa mostram os locais.

É essencial ao conectar um novo recurso ou componente a um sistema antigo e complicado.

Você não pode fazer isso facilmente em C ++, sem uma ferramenta sofisticada de construção de gráficos de chamadas.


0

A maioria das pessoas parece pensar que C e C ++ estão de alguma forma relacionados, mas estão redondamente enganados. C ++ é uma linguagem completamente diferente de C.

Em C ++, você pensa em termos de objetos e como eles se relacionam uns com os outros. Em C, você pensa em termos de APIs. É como a diferença entre o dia e 17.

Uma analogia pobre: ​​se alguém adicionar chinês ao inglês e chamá-lo de inglês ++, você provavelmente não se sentiria confortável em adicionar uma frase em chinês à sua última carta de amor, porque é muito mais fácil expressar amor nesta parte do inglês ++.


0

A seguir estão todas as razões pelas quais pode ser benéfico limitar um projeto a C:

  • compilação mais rápida porque a linguagem é muito mais simples
  • requer menos suporte de tempo de execução, tornando-os ambientes de baixo nível mais adequados
  • muito mais fácil de interagir com outros idiomas
  • suporta arrays de tamanhos variáveis ​​na pilha
  • mais fácil de ler o código assembly porque não há alteração de nome
  • permite que o código produzido por diferentes compiladores seja facilmente combinado, uma vez que é a interface binária padrão do aplicativo
Ao utilizar nosso site, você reconhece que leu e compreendeu nossa Política de Cookies e nossa Política de Privacidade.
Licensed under cc by-sa 3.0 with attribution required.