2009-09-20 14 views
9

Al haber aprendido Java y C++, aprendí el método OO-way. Quiero embarcarme en un proyecto bastante ambicioso, pero quiero hacerlo en C. Sé cómo dividir los problemas en clases y cómo convertirlas en jerarquías de clase. Sé cómo abstraer la funcionalidad en clases e interfaces abstractas. Incluso soy bastante hábil en el uso del polimorfismo de una manera efectiva.C para un programador orientado a objetos

El problema es que cuando me presentan un problema, la única manera que sé de hacerlo es de una manera orientada a objetos. Me volví demasiado dependiente de las filosofías y metodologías de diseño orientadas a objetos.

Quiero aprender a pensar de una manera estrictamente procedimental. ¿Cómo hago las cosas en un mundo que carece de clases, interfaces, polimorfismo, sobrecarga de funciones, constructores, etc.

¿Cómo se representan conceptos complejos usando solo struct s no orientado a objetos? ¿Cómo se soluciona la falta de sobrecarga de funciones? ¿Cuáles son algunos consejos y trucos para pensar de forma procesal?

+1

Esto podría interesarte http://www.planetpdf.com/developer/article.asp?ContentID=6635 Es un poco anticuado, pero gratis. – Lucas

Respuesta

1

Creo que tienes un buen plan. Hacer las cosas completamente en forma de OO en C, si bien es bastante posible, es suficiente pena que pronto lo dejes caer de todos modos. (No pelee el idioma.)

Si desea una declaración filosófica sobre cómo mapear el camino OO al modo C, en parte sucede al empujar la creación de objetos hasta un nivel. Un módulo aún puede implementar su objeto como una caja negra, y aún puede usar un estilo de programación razonable, pero básicamente es demasiado doloroso para ocultar realmente el objeto, por lo que la persona que llama lo asigna y lo pasa, en lugar de asignarlo al módulo. y devolverlo nuevamente. Por lo general, apuntas en getters y setters, o los implementas como macros.

Considera también que todas las abstracciones que mencionaste son una capa relativamente delgada además del ordinario structs, por lo que no estás muy lejos de lo que quieres hacer. Simplemente no está bien empaquetado.

0

La forma estándar de comportamiento polimórfico en C es utilizar punteros de función. Encontrará una gran cantidad de API C (como las estándar qsort(3) y bsearch(3)) que toman indicadores de función como parámetros; algunos no estándar como qsort_r toman un puntero a la función y un contexto puntero (thunk en este caso) que no tiene otra finalidad que no sea volver a pasar a la función de devolución de llamada. El puntero de contexto funciona exactamente como el puntero this en los lenguajes orientados a objetos, cuando se trata de objetos funcionales (por ejemplo, functors).

Consulte también:

1

El C juego de herramientas se compone de funciones, punteros de función y macros. Los punteros de función se pueden usar para emular el polimorfismo.

1

Usted está tomando el viaje inverso que los viejos programadores de C hicieron para aprender OO.

Incluso antes era un techniquis standart OO se utilizaron C++ en C.

Incluyeron definir estructuras con un puntero a srtuct (normalmente llamado a este ...) Entonces definir funciones de puntero en la estructura, y durante el tiempo de ejecución inicialice esos punteros a las funciones relevantes. Todas las funciones recibidas como primer paremeter al puntero struct esto.

+1

"esto" no tiene sentido como miembro de la estructura, sino como un parámetro en la convención de llamadas a funciones (generalmente la primera). – fortran

+0

también puede llamarlo a mí, a mí o a cualquier cosa que desee. pero nombrar esto podría tener más sentido si está familiarizado con OO. – Amirshk

+2

Nombrarlo 'this' tiene la desventaja de que nunca se puede compilar el código con un compilador de C++ (que considera' this' una palabra clave). Y hay OO idiomas que lo llaman 'self' y (IIRC, de todos modos)' me'. Si tiene un fondo _general_ OO (a diferencia de un fondo de lenguaje OO derivado de C), 'this' no necesariamente tiene más sentido que otros nombres. – sbi

4

La forma de procedimiento es, por un lado, tener sus estructuras de datos y, por otro lado, sus algoritmos. Luego tomas tus estructuras de datos y las pasas a tus algoritmos. Sin encapsulamiento, se necesita una cantidad de disciplina algo mayor para hacer esto y si aumenta el nivel de abstracción para que sea más fácil hacerlo bien, está haciendo una parte considerable de OO en C.

0

No lo crea tiene que dejar de lado su conocimiento del trabajo orientado a objetos: puede "program into the language".

Tuve que trabajar en C después de haber experimentado principalmente en el trabajo orientado a objetos. C permite que algún nivel de conceptos de objetos se desarrolle. En el trabajo, tuve que implementar un árbol rojo-negro en C, para usar en un sweep-line algorithm para encontrar los puntos de intersección en un conjunto de segmentos. Dado que el algoritmo utilizó diferentes funciones de comparación, terminé usando punteros de función para lograr el mismo efecto que lambdas en Scheme o delegados en C#. Funcionó bien y también permitió que el árbol equilibrado fuera reutilizable.

La otra característica del árbol equilibrado era el uso de punteros vacíos para almacenar datos arbitrarios. Nuevamente, los indicadores de vacío y función en C son un problema (si no conoce sus pormenores), pero se pueden usar para aproximar la creación de una estructura de datos genérica.

Una última nota: utilice la herramienta adecuada para el trabajo. Si desea utilizar C simplemente para dominar la técnica de procedimiento, elija un problema que sea adecuado para un enfoque de procedimiento. No tuve elección en el asunto (aplicación heredada escrita en C, y la gente demanda el mundo y se niega a ingresar al siglo XXI), así que tuve que ser creativo. C es ideal para abstracciones bajas/medias de la máquina, por ejemplo, si desea escribir un programa de inspección de paquetes de línea de comandos.

1

No piense C en la forma de OOP completa. Si tiene que usar C, debe aprender la programación de procedimientos. Hacer esto no tomaría más tiempo que aprender a realizar todas las características de OOP en C. Además, la encapsulación básica probablemente esté bien, pero muchas otras características de OOP vienen con una sobrecarga en el rendimiento cuando las imita (no cuando el lenguaje está diseñado para apoyar OOP). La sobrecarga puede ser enorme si sigues estrictamente la metodología de diseño C++ para representar cada pequeña cosa como un objeto. Los lenguajes de programación tienen propósitos específicos en el diseño. Cuando rompes el límite, siempre tienes que pagar algo a cambio del costo.

Cuestiones relacionadas