¿Es una buena costumbre usar expresiones C en código C ++?


19

En la escuela comenzamos a aprender C este año, a pesar de que estoy muy por delante de la clase, y aprendí Java, C ++ y C mientras la clase está en la base de C. De todos modos, me he estado documentando, leyendo libros, artículos, y le pregunté a mi maestra por qué debería aprender C, y ella dijo que era la base de C ++. Cuando comencé a programar, encontré que C ++ era mucho más fácil, luego aprendí C. Pero en los libros se puede ver que el código C funciona en C ++, pero no va al revés.

Mi pregunta es bastante directa ~ ¿Es un buen hábito usar expresiones C en C ++? Dejame darte un ejemplo:

Debería este código

#include <stdio.h>
#include <iostream>

int main() {
int x;
scanf("%d", &x);
cout << "The number you entered is " << x << "And it's double is " << x*x;
return 0;
}

Sea más eficiente o mejor de alguna manera que esto:

#include <iostream>

int main() {
int x;
cin >> x;
cout << "The number you entered is " << x << "And it's double is " << x*x;
return 0;
}

Ya he hecho una documentación sencilla sobre esto en algunos libros viejos y polvorientos, y por lo que pude encontrar, usar scanf en lugar de cout también elimina el flujo o algo así, así que básicamente estoy preguntando si es mejor usar scanf y en que contextos

Esto también se aplica al archivo IO, ya que siempre he encontrado que File IO es más fácil en C que en C ++. Esta pregunta se aplica a casi todas las expresiones generales en C aplicadas a C ++. También es notable que estoy usando un compilador moderno y, sin embargo, esto no debería importar, ya que estoy preguntando si es un buen hábito de programación usar expresiones C en código C ++.

Probablemente hay inconvenientes y ventajas de hacer esto, pero solo estoy buscando un tipo de respuesta de sí / por qué, no / por qué.

Además, si hay algún detalle que he dejado fuera, publique un comentario.


12
Tenga mucho cuidado con la mezcla stdioy iostream. Hay cierto orden y sincronización garantizados dentro de una familia que no necesariamente se aplican fuera de ella.
David Thornley

Gracias por el consejo, pero ese desecho de código fue un puro ejemplo. Gracias de cualquier manera.
Bugster

25
Si estás aprendiendo programación; ¡ Debes aprender la sangría adecuada!
bitmask

55
scanf () no es un gran ejemplo; es tan propenso a errores de uso que le aconsejaría que lo evite en C o C ++.
Russell Borogove

1
Podría haber sido solo un código de muestra, pero el comentario de David realmente llega al meollo del problema por el que no debe usar modismos C al programar en C ++. Son idiomas completamente diferentes; no los confunda más de lo que confunde Java y C, o C ++ y Visual Basic.
Cody Gray

Respuestas:


36

No, es un mal hábito. Cuando haga esto para ganarse la vida, es probable que termine violando las guías de estilo a las que se adhiere su equipo (o al menos se sorprenderá durante las revisiones de código).

Sí, funciona, pero si hay un equivalente de C ++, úsalo. (por ejemplo, trate de no mezclarse printfscon couts)


+1 - Corto y al grano. Y esto resalta el punto principal en mi respuesta de que las pautas del equipo ayudan a unir a las personas y unificarlas para que puedan trabajar juntas.
jmort253

Este comentario responde bastante bien a mi pregunta y trae un argumento sólido. Gracias.
Bugster

1
@ThePlan gracias. todos tuvieron excelentes respuestas para esta pregunta.
jglouie

1
Nota: el uso printfconstante funcionará tan bien como el uso coutconstante. Los únicos problemas son mezclarlos y el estilo.
user253751

¿Puedes dar un ejemplo de una característica en C que no tenga un equivalente en C ++?
klutt

20

En general, C y C ++ se consideran como si fueran dos lenguajes completamente separados. Por lo tanto, puede considerarse una mala forma usar la sintaxis de C en un programa de C ++.

Estás en lo correcto; sin embargo, ese código C se compilará muy bien. Realmente depende de cuán flexible sea su empresa en términos de seguir los estándares. Si alguna vez me hicieran la pregunta en una entrevista, me aseguraría de hacerle saber al entrevistador que C funciona en C ++, pero también que C y C ++ son dos lenguajes separados y probablemente no deberían mezclarse a menos que haya un muy, muy Buena razón para hacerlo.

Otra cosa a considerar es que los estándares ayudan a crear una plataforma donde más personas pueden trabajar fácilmente con el código. Si bien tuvo la suerte de tener un maestro que lo alentó a aprender C, no todos pueden ser tan afortunados. Por lo tanto, mezclar C en un programa C ++ podría ser confuso para alguien que nunca había aprendido C.

En resumen, solo porque puedes hacer algo no significa que debas hacerlo, y solo porque no debes hacer algo no significa que no puedas :)


Veo. ¿Qué pasa con la funcionalidad? ¿Hay casos particulares en los que la sintaxis C es mejor que la sintaxis C ++?
Bugster

10

C ++ es retrocompatible con C por diseño, por lo que generalmente el código C será compilado por el compilador de C ++ muy bien ( generalmente porque hay palabras reservadas adicionales en C ++ que no están en C, y podrían usarse en el código C rompiendo la compilación).

Sin embargo, lo veo como una mala práctica mezclar código. Si usa scanf- use printf, si está usando operator >>- use operator <<. La razón es que los operadores de C ++ sobrecargados pueden encapsular funcionalidades de las que no eres consciente, y si no coinciden, tu programa hará cosas que no querías que hiciera.

No hay una razón particular para preferir la sintaxis de C en el código de C ++, estos son lenguajes diferentes, y cuando se usa la sintaxis de C en el código de C ++, todavía está escribiendo código de C ++ , pero no está utilizando muchas de sus potentes herramientas.


55
La incompatibilidad entre C y C ++ es más que solo palabras clave. El sistema de escritura cambia, y hay características que existen en C (especialmente C99), que no existen en C ++. (Por ejemplo, matrices de longitud variable).
Arafangion

9

Si dejamos de lado el estilo de codificación y los problemas estéticos, también hay varios problemas técnicos que enfrenta al usar C en código C ++:

  • ¿Qué es la C? C90, C99 o C11? Puede haber varios problemas de compatibilidad según el estándar C que esté utilizando. Tipo booleano, // comentarios, características C99 como VLA, inicializadores designados, etc.

  • C ++ tiene una escritura más estricta que C. Para compilar el código C en C ++, lo más probable es que deba agregar varios tipos de letra para obtener el tipo esperado. Esto significa que es posible que deba volver a escribir código C perfectamente bien y con calidad de producción para que funcione en C ++.

  • Los tipos de letra enfocados por una escritura más estricta generalmente son algo bueno, pero en algunos casos pueden introducir u ocultar errores. Tome el infame elenco del resultado de malloc () como ejemplo. Esto debería ser encasillado en C ++, pero nunca en C. (1)

  • La combinación de la funcionalidad C y C ++ puede provocar errores y un comportamiento indefinido. Por ejemplo, no funcionará asignar con malloc () y liberar con eliminar . (2)

  • Temas de seguridad del hilo. La biblioteca estándar de C no es segura para subprocesos. La biblioteca estándar de C ++ puede o no ser segura para subprocesos, si lo es, entonces agregar llamadas a la función de la biblioteca C a su código lo destruirá.

    Como nota al margen para los programadores de Windows: el compilador de Visual C ++ tuvo un error de fuga durante bastante tiempo, cuando la función CreateThread () de la API de Windows se usó en el mismo programa que la biblioteca C. (3, 4)

  • La convención de llamada podría ser un problema en algunos compiladores, lo que obligaría a uno a utilizarla extern "C"para indicar explícitamente qué funciones deberían vincularse con la "convención de llamada C".

  • Detalles molestos. El operador de coma se comporta de manera diferente. La coma final en las declaraciones struct / enum está permitida en C99 / C11 pero no en C ++. El alcance de varios tipos de variables y funciones se trata de manera diferente. Etcétera etcétera.

Es probable que haya incluso más casos.


Referencias

  1. http://c-faq.com/malloc/cast.html
  2. http://www.parashift.com/c++-faq-lite/freestore-mgmt.html#faq-16.3
  3. http://www.flounder.com/badprogram.htm#CreateThread
  4. http://msdn.microsoft.com/en-us/library/windows/desktop/ms682453%28v=vs.85%29.aspx

7

La razón por la cual C ++ puede compilar C es solo por "compatibilidad con versiones anteriores" (evite reescribir el código de trabajo existente).

Pero C ++ tiene una filosofía diferente con respecto a c. Mezclarlos no les hace un buen servicio a ambos.

La forma en que C y C ++ administran las E / S puede confiar en una forma diferente de administrar el estado interno de las E / S. Entonces, al menos, use la entrada y la salida de manera consistente.

Y en los programas de C ++ respeta el estilo de C ++ (a menos que se requiera específicamente hacerlo en otro lugar)


5

Yo diría que aprender C primero es, en mi humilde opinión, una buena idea. De esta manera, las personas comienzan a comprender el hardware para el que escriben el software.

Sin embargo, mezclar estos dos idiomas no es necesariamente una buena idea. Porque obtienes la increíble complejidad de C ++ junto con un poco de twiddling en bruto común a C.

Como puede ver, incluso en un ejemplo tan simple como el suyo, hay problemas de sincronización con diferentes tipos de secuencias y almacenamiento en búfer interno. Pero también, el enfoque C & C ++ no es más flexible de ninguna manera. Cambie a la clase x, y no hay operadores para usar la transmisión y esas cosas.

Es complicado...

Realmente creo que un buen programador de C ++ debería saber cómo se voltean los bits detrás de cada construcción y cuáles son los comportamientos ocultos.

Pero aprender C ++, al menos más del 50%, requiere más de 5 años de codificación profesional, y simplemente no se puede administrar eso en el plan de estudios, que dura 6 meses con aproximadamente 20 horas de experiencia práctica.

Si usara construcciones de C ++ en C, no usaría flujos, son muy simples desde la vista de pájaro y hacen que la gente crea que el desarrollo de software es fácil, pero oculta complejidades adicionales sin muchos beneficios en muchas situaciones.

Sin embargo, las clases de contenedor RAII, las plantillas, las sobrecargas, la corrección constante y las clases abstractas puras para interfaces comunes (no use la forma f-ng de Java, ¡POR FAVOR!) Son buenos candidatos. Porque agregan seguridad, generalidad y facilidad de uso que son muy importantes para proyectos de la vida real. Sin embargo, asegúrese de recordar cosas como la destrucción virtual, la naturaleza explosiva de la construcción de copia predeterminada, la sobrecarga de tiempo de ejecución, la corrección constante, etc.

Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.