stringtranslate.com

Programación orientada a objetos

Notación UML para una clase. Esta clase Button tiene variables para datos y funciones . Mediante la herencia, se puede crear una subclase como un subconjunto de la clase Button. Los objetos son instancias de una clase.

La programación orientada a objetos ( POO ) es un paradigma de programación basado en el concepto de objetos , [1] que pueden contener datos y código : datos en forma de campos (a menudo conocidos como atributos o propiedades ), y código en forma de procedimientos (a menudo conocidos como métodos ). En la POO, los programas informáticos se diseñan a partir de objetos que interactúan entre sí. [2] [3]

Muchos de los lenguajes de programación más utilizados (como C++ , Java , [4] y Python ) son multiparadigma y admiten la programación orientada a objetos en mayor o menor grado, normalmente en combinación con programación imperativa , programación procedimental y programación funcional .

Los lenguajes orientados a objetos más importantes incluyen Ada , ActionScript , C++ , Common Lisp , C# , Dart , Eiffel , Fortran 2003 , Haxe , Java , [4] JavaScript , Kotlin , Logo , MATLAB , Objective-C , Object Pascal , Perl , PHP , Python , R , Raku , Ruby , Scala , SIMSCRIPT , Simula , Smalltalk , Swift , Vala y Visual Basic.NET .

Historia

La terminología que invoca "objetos" en el sentido moderno de la programación orientada a objetos hizo su primera aparición en el grupo de inteligencia artificial del MIT a finales de los años 1950 y principios de los 1960. "Objeto" se refería a átomos de LISP con propiedades identificadas (atributos). [5] [6] Otro ejemplo temprano del MIT fue Sketchpad creado por Ivan Sutherland en 1960-1961; en el glosario del informe técnico de 1963 basado en su disertación sobre Sketchpad, Sutherland definió las nociones de "objeto" e "instancia" (con el concepto de clase cubierto por "maestro" o "definición"), aunque especializado en la interacción gráfica. [7] Además, en 1968, una versión de ALGOL del MIT , AED-0, estableció un vínculo directo entre las estructuras de datos ("plexes", en ese dialecto) y los procedimientos, prefigurando lo que más tarde se denominaría "mensajes", "métodos" y "funciones miembro". [8] [9] Temas como la abstracción de datos y la programación modular fueron puntos de discusión comunes en esta época.

Independientemente del trabajo posterior del MIT, como AED, Simula se desarrolló durante los años 1961-1967. [8] Simula introdujo conceptos importantes que hoy son una parte esencial de la programación orientada a objetos, como clase y objeto , herencia y enlace dinámico . [10] El lenguaje de programación orientado a objetos Simula fue utilizado principalmente por investigadores involucrados con el modelado físico , como modelos para estudiar y mejorar el movimiento de barcos y su contenido a través de puertos de carga. [10]

Pensé que los objetos eran como células biológicas y/o computadoras individuales en una red, capaces de comunicarse solo con mensajes (por eso la mensajería apareció desde el principio; llevó un tiempo ver cómo enviar mensajes en un lenguaje de programación lo suficientemente eficiente como para que fuera útil).

Alan Kay, [1]

Influenciado por el trabajo del MIT y el lenguaje Simula, en noviembre de 1966 Alan Kay comenzó a trabajar en ideas que eventualmente serían incorporadas al lenguaje de programación Smalltalk . Kay utilizó el término "programación orientada a objetos" en conversaciones ya en 1967. [1] Aunque a veces se le llama "el padre de la programación orientada a objetos", [11] Alan Kay ha diferenciado su noción de OO de la noción más convencional de tipo de datos abstractos de objeto, y ha dado a entender que el establishment de la ciencia informática no adoptó su noción. [1] Un memorándum del MIT de 1976 coescrito por Barbara Liskov enumera Simula 67 , CLU y Alphard como lenguajes orientados a objetos, pero no menciona a Smalltalk. [12]

En la década de 1970, Alan Kay , Dan Ingalls y Adele Goldberg desarrollaron la primera versión del lenguaje de programación Smalltalk en Xerox PARC . Smalltalk-72 incluía un entorno de programación y estaba tipado dinámicamente , y al principio era interpretado , no compilado . Smalltalk se hizo conocido por su aplicación de la orientación a objetos a nivel de lenguaje y su entorno de desarrollo gráfico. Smalltalk pasó por varias versiones y el interés en el lenguaje creció. [13] Si bien Smalltalk fue influenciado por las ideas introducidas en Simula 67, fue diseñado para ser un sistema completamente dinámico en el que las clases se podían crear y modificar dinámicamente. [14]

A finales de los años 1970 y 1980, la programación orientada a objetos cobró importancia. El Lisp orientado a objetos Flavors se desarrolló a partir de 1979, introduciendo la herencia múltiple y los mixins . [15] En 1981, Goldberg editó la edición de agosto de Byte Magazine , presentando Smalltalk y la programación orientada a objetos a una amplia audiencia. [16] LOOPS, el sistema de objetos para Interlisp -D, fue influenciado por Smalltalk y Flavors, y se publicó un artículo al respecto en 1982. [17] En 1986, la Association for Computing Machinery organizó la primera Conferencia sobre Programación, Sistemas, Lenguajes y Aplicaciones Orientadas a Objetos (OOPSLA), a la que asistieron 1000 personas. Entre otros desarrollos estuvo el Common Lisp Object System , que integra la programación funcional y la programación orientada a objetos y permite la extensión a través de un protocolo Meta-objeto . En la década de 1980, hubo algunos intentos de diseñar arquitecturas de procesador que incluyeran soporte de hardware para objetos en memoria, pero no tuvieron éxito. Algunos ejemplos incluyen el Intel iAPX 432 y el Linn Smart Rekursiv .

A mediados de la década de 1980, Brad Cox , que había utilizado Smalltalk en ITT Inc. , desarrolló Objective-C . Bjarne Stroustrup , que había utilizado Simula para su tesis doctoral, creó el lenguaje orientado a objetos C++ . [13] En 1985, Bertrand Meyer también produjo el primer diseño del lenguaje Eiffel . Centrado en la calidad del software, Eiffel es un lenguaje de programación puramente orientado a objetos y una notación que soporta todo el ciclo de vida del software. Meyer describió el método de desarrollo de software Eiffel, basado en un pequeño número de ideas clave de la ingeniería de software y la informática, en Object-Oriented Software Construction . [18] Esencial para el enfoque de calidad de Eiffel es el mecanismo de confiabilidad de Meyer, el diseño por contrato , que es una parte integral tanto del método como del lenguaje.

A principios y mediados de la década de 1990, la programación orientada a objetos se desarrolló como el paradigma de programación dominante cuando los lenguajes de programación que soportaban las técnicas se hicieron ampliamente disponibles. Estos incluyeron Visual FoxPro 3.0, [19] [20] C++ , [21] y Delphi [ cita requerida ] . Su dominio se vio reforzado aún más por la creciente popularidad de las interfaces gráficas de usuario , que dependen en gran medida de las técnicas de programación orientada a objetos. Un ejemplo de una biblioteca de GUI dinámica y un lenguaje OOP estrechamente relacionados se puede encontrar en los marcos Cocoa en Mac OS X , escritos en Objective-C , una extensión de mensajería dinámica orientada a objetos para C basada en Smalltalk. Los kits de herramientas OOP también aumentaron la popularidad de la programación basada en eventos (aunque este concepto no se limita a la OOP).

En la ETH de Zúrich , Niklaus Wirth y sus colegas investigaron el concepto de verificación de tipos a través de los límites de los módulos. Modula-2 (1978) incluyó este concepto, y su diseño posterior, Oberon (1987), incluyó un enfoque distintivo para la orientación a objetos, clases y demás. La herencia no es obvia en el diseño de Wirth, ya que su nomenclatura mira en la dirección opuesta: se llama extensión de tipo y el punto de vista es desde el padre hasta el heredero.

Se han añadido características orientadas a objetos a muchos lenguajes que ya existían, como Ada , BASIC , Fortran , Pascal y COBOL . Añadir estas características a lenguajes que no estaban diseñados inicialmente para ellas solía generar problemas de compatibilidad y mantenimiento del código.

Más recientemente, han surgido algunos lenguajes que son principalmente orientados a objetos, pero que también son compatibles con la metodología procedimental. Dos de estos lenguajes son Python y Ruby . Probablemente los lenguajes orientados a objetos recientes más importantes comercialmente sean Java , desarrollado por Sun Microsystems , así como C# y Visual Basic.NET (VB.NET), ambos diseñados para la plataforma .NET de Microsoft . Cada uno de estos dos marcos muestra, a su manera, el beneficio de usar OOP al crear una abstracción a partir de la implementación. VB.NET y C# admiten la herencia entre lenguajes, lo que permite que las clases definidas en un lenguaje creen subclases de las clases definidas en el otro lenguaje.

Características

La programación orientada a objetos utiliza objetos, pero no todas las técnicas y estructuras asociadas se admiten directamente en lenguajes que afirman admitir la programación orientada a objetos. Las características que se enumeran a continuación son comunes entre los lenguajes considerados como fuertemente orientados a objetos y clases (o multiparadigma con soporte de programación orientada a objetos), con notables excepciones mencionadas. [22] [23] [24] [25] Christopher J. Date afirmó que la comparación crítica de la programación orientada a objetos con otras tecnologías, en particular la relacional, es difícil debido a la falta de una definición acordada y rigurosa de la programación orientada a objetos. [26]

Compartido con lenguajes no OOP

La compatibilidad con la programación modular permite agrupar procedimientos en archivos y módulos con fines organizativos. Los módulos tienen espacios de nombres para que los identificadores de un módulo no entren en conflicto con un procedimiento o una variable que compartan el mismo nombre en otro archivo o módulo.

Objetos

Un objeto es una estructura de datos o un tipo de datos abstracto que contiene campos ( variables de estado que contienen datos) y métodos ( subrutinas o procedimientos que definen el comportamiento del objeto en código). Los campos también pueden conocerse como miembros, atributos o propiedades. Los objetos se almacenan normalmente como regiones contiguas de memoria . Se accede a los objetos de forma similar a las variables con estructuras internas complejas y, en muchos lenguajes, son efectivamente punteros , que sirven como referencias reales a una única instancia de dicho objeto en la memoria dentro de un montón o pila.

Los objetos a veces corresponden a cosas que se encuentran en el mundo real. [27] Por ejemplo, un programa de gráficos puede tener objetos como "círculo", "cuadrado" y "menú". Un sistema de compras en línea puede tener objetos como "carrito de compras", "cliente" y "producto". A veces, los objetos representan entidades más abstractas, como un objeto que representa un archivo abierto o un objeto que proporciona el servicio de traducir medidas del sistema métrico decimal al sistema métrico de EE. UU.

Los objetos pueden contener otros objetos en sus variables de instancia; esto se conoce como composición de objetos . Por ejemplo, un objeto en la clase Employee puede contener (ya sea directamente o a través de un puntero) un objeto en la clase Address, además de sus propias variables de instancia como "first_name" y "position". La composición de objetos se utiliza para representar relaciones "tiene un": cada empleado tiene una dirección, por lo que cada objeto Employee tiene acceso a un lugar para almacenar un objeto Address (ya sea directamente incrustado dentro de sí mismo o en una ubicación separada a la que se accede a través de un puntero). Date y Darwen han propuesto una base teórica que utiliza OOP como una especie de sistema de tipos personalizable para soportar RDBMS , pero prohíbe los punteros a objetos. [28]

El paradigma OOP ha sido criticado por enfatizar demasiado el uso de objetos para el diseño y modelado de software a expensas de otros aspectos importantes (computación/algoritmos). [29] [30] Por ejemplo, Rob Pike ha dicho que los lenguajes OOP frecuentemente cambian el foco de las estructuras de datos y algoritmos a los tipos . [31] Steve Yegge señaló que, a diferencia de la programación funcional : [32]

La programación orientada a objetos pone a los sustantivos en primer lugar. ¿Por qué tomarse tantas molestias para poner una parte del discurso en un pedestal? ¿Por qué un tipo de concepto debería tener prioridad sobre otro? No es que la programación orientada a objetos haya hecho que los verbos perdieran importancia de repente en nuestra forma de pensar. Es una perspectiva extrañamente sesgada.

Rich Hickey , creador de Clojure , describió los sistemas de objetos como modelos demasiado simplistas del mundo real. Hizo hincapié en la incapacidad de la programación orientada a objetos para modelar el tiempo de forma adecuada, lo que se está volviendo cada vez más problemático a medida que los sistemas de software se vuelven más concurrentes. [30]

Alexander Stepanov compara desfavorablemente la orientación a objetos con la programación genérica : [29]

Considero que la programación orientada a objetos es técnicamente errónea. Intenta descomponer el mundo en términos de interfaces que varían en función de un único tipo. Para abordar los problemas reales se necesitan álgebras multiclasificadas, es decir, familias de interfaces que abarcan múltiples tipos. Considero que la programación orientada a objetos es filosóficamente errónea. Afirma que todo es un objeto. Incluso si fuera cierto, no es muy interesante: decir que todo es un objeto es no decir nada en absoluto.

Herencia

Los lenguajes OOP son diversos, pero por lo general permiten la herencia para la reutilización y extensibilidad del código en forma de clases o prototipos . Estas formas de herencia son significativamente diferentes, pero se utiliza una terminología análoga para definir los conceptos de objeto e instancia .

Basado en clases

En la programación basada en clases , el estilo más popular, se requiere que cada objeto sea una instancia de una clase particular . La clase define el formato o tipo de datos (incluidas las variables miembro y sus tipos) y los procedimientos disponibles (métodos de clase o funciones miembro) para un tipo o clase de objeto determinado. Los objetos se crean llamando a un tipo especial de método en la clase conocido como constructor . Las clases pueden heredar de otras clases, por lo que se organizan en una jerarquía que representa relaciones de "es-un-tipo-de". Por ejemplo, la clase Empleado puede heredar de la clase Persona. Todos los datos y métodos disponibles para la clase principal también aparecen en la clase secundaria con los mismos nombres. Por ejemplo, la clase Persona puede definir las variables "nombre" y "apellido" con el método "make_full_name()". Estas también estarán disponibles en la clase Empleado, que puede agregar las variables "posición" y "salario". Se garantiza que todas las instancias de la clase Empleado tendrán las mismas variables, como el nombre, la posición y el salario. Los procedimientos y las variables pueden ser específicos de la clase o de la instancia; Esto nos lleva a los siguientes términos:

Dependiendo de la definición del lenguaje, las subclases pueden o no ser capaces de anular los métodos definidos por las superclases. La herencia múltiple está permitida en algunos lenguajes, aunque esto puede hacer que la resolución de anulaciones sea complicada. Algunos lenguajes tienen soporte especial para otros conceptos como rasgos y mixins , aunque, en cualquier lenguaje con herencia múltiple, un mixin es simplemente una clase que no representa una relación de tipo "es-un-tipo-de". Los mixins se usan típicamente para agregar los mismos métodos a múltiples clases. Por ejemplo, la clase UnicodeConversionMixin podría proporcionar un método unicode_to_ascii() cuando se incluye en la clase FileReader y la clase WebPageScraper, que no comparten un padre común.

Las clases abstractas no pueden instanciarse en objetos; existen solo para la herencia en otras clases "concretas" que sí pueden instanciarse. En Java, la finalpalabra clave se puede utilizar para evitar que una clase se subclasifique. [33]

Basado en prototipos

En cambio, en la programación basada en prototipos , los objetos son las entidades primarias. Generalmente, el concepto de una "clase" ni siquiera existe. Más bien, el prototipo o padre de un objeto es simplemente otro objeto al que el objeto está vinculado. En Self, un objeto puede tener varios padres o ninguno, [34] pero en el lenguaje basado en prototipos más popular, Javascript, cada objeto tiene un vínculo de prototipo (y solo uno). Se pueden crear nuevos objetos basados ​​en objetos ya existentes elegidos como su prototipo. Puede llamar a dos objetos diferentes manzana y naranja una fruta si el objeto fruta existe, y tanto manzana como naranja tienen fruta como su prototipo. La idea de la clase fruta no existe explícitamente, pero se puede modelar como la clase de equivalencia de los objetos que comparten el mismo prototipo, o como el conjunto de objetos que satisfacen una cierta interfaz ( tipado de pato ). A diferencia de la programación basada en clases, normalmente es posible en los lenguajes basados ​​en prototipos definir atributos y métodos que no se comparten con otros objetos; por ejemplo, el atributo sugar_content se puede definir en manzana pero no en naranja .

Ausencia

Algunos lenguajes como Go no admiten la herencia en absoluto. Go afirma que está orientado a objetos [35] y Bjarne Stroustrup, autor de C++, ha afirmado que es posible hacer programación orientada a objetos sin herencia [36] . La doctrina de la composición sobre la herencia aboga por implementar relaciones de tipo tiene un usando la composición en lugar de la herencia. Por ejemplo, en lugar de heredar de la clase Persona, la clase Empleado podría dar a cada objeto Empleado un objeto Persona interno, que luego tendría la oportunidad de ocultar del código externo incluso si la clase Persona tiene muchos atributos o métodos públicos. La delegación es otra característica del lenguaje que se puede usar como alternativa a la herencia.

Rob Pike ha criticado la mentalidad OO por preferir una jerarquía de tipos multinivel con abstracciones en capas a una tabla de búsqueda de tres líneas . [37] Ha llamado a la programación orientada a objetos "los números romanos de la informática". [38]

Bob Martin afirma que, debido a que son software, las clases relacionadas no necesariamente comparten las relaciones de las cosas que representan. [39]

Envío dinámico de mensajes

Es responsabilidad del objeto, no de ningún código externo, seleccionar el código procedimental que se ejecutará en respuesta a una llamada de método, normalmente buscando el método en tiempo de ejecución en una tabla asociada con el objeto. Esta característica se conoce como despacho dinámico . Si la variabilidad de la llamada depende de más de un tipo de objeto en el que se llama (es decir, al menos otro objeto de parámetro está involucrado en la elección del método), se habla de despacho múltiple . Una llamada de método también se conoce como paso de mensajes . Se conceptualiza como un mensaje (el nombre del método y sus parámetros de entrada) que se pasa al objeto para su envío.

El envío interactúa con la herencia; si un método no está presente en un objeto o clase determinados, el envío se delega a su objeto o clase padre, y así sucesivamente, subiendo por la cadena de herencia.

Abstracción y encapsulación de datos

La abstracción de datos es un patrón de diseño en el que los datos son visibles solo para funciones relacionadas semánticamente, para evitar un mal uso. El éxito de la abstracción de datos conduce a la incorporación frecuente de la ocultación de datos como un principio de diseño en la programación funcional pura y orientada a objetos. De manera similar, la encapsulación evita que el código externo se ocupe del funcionamiento interno de un objeto. Esto facilita la refactorización del código , por ejemplo, permitiendo al autor de la clase cambiar la forma en que los objetos de esa clase representan sus datos internamente sin cambiar ningún código externo (siempre que las llamadas a métodos "públicos" funcionen de la misma manera). También alienta a los programadores a poner todo el código que se ocupa de un determinado conjunto de datos en la misma clase, lo que lo organiza para que otros programadores lo comprendan fácilmente. La encapsulación es una técnica que fomenta el desacoplamiento .

En la programación orientada a objetos, los objetos proporcionan una capa que se puede utilizar para separar el código interno del externo e implementar la abstracción y la encapsulación. El código externo solo puede utilizar un objeto llamando a un método de instancia específico con un determinado conjunto de parámetros de entrada, leyendo una variable de instancia o escribiendo en una variable de instancia. Un programa puede crear muchas instancias de objetos a medida que se ejecuta, que operan de forma independiente. Se afirma que esta técnica permite una fácil reutilización de los mismos procedimientos y definiciones de datos para diferentes conjuntos de datos, además de reflejar potencialmente las relaciones del mundo real de forma intuitiva. En lugar de utilizar tablas de bases de datos y subrutinas de programación, el desarrollador utiliza objetos con los que el usuario puede estar más familiarizado: objetos de su dominio de aplicación. [40] Estas afirmaciones de que el paradigma OOP mejora la reutilización y la modularidad han sido criticadas. [41] [42]

Si una clase no permite llamar a código para acceder a los datos internos de un objeto y permite el acceso solo a través de métodos, también se trata de una forma de ocultar información. Algunos lenguajes (Java, por ejemplo) permiten que las clases impongan restricciones de acceso explícitamente, por ejemplo, denotando datos internos con la privatepalabra clave y designando métodos destinados a ser utilizados por código fuera de la clase con la publicpalabra clave. [43] Los métodos también pueden diseñarse como públicos, privados o de nivel intermedio como protected(que permite el acceso desde la misma clase y sus subclases, pero no a objetos de una clase diferente). [43] En otros lenguajes (como Python) esto se aplica solo por convención (por ejemplo, privatelos métodos pueden tener nombres que comiencen con un guión bajo ). En los lenguajes C#, Swift y Kotlin, internalla palabra clave permite el acceso solo a archivos presentes en el mismo ensamblaje, paquete o módulo que el de la clase. [44]

En los lenguajes de programación, en particular los orientados a objetos, el énfasis en la abstracción es vital. Los lenguajes orientados a objetos amplían la noción de tipo para incorporar la abstracción de datos, destacando la importancia de restringir el acceso a los datos internos a través de métodos. [45] Eric S. Raymond ha escrito que los lenguajes de programación orientados a objetos tienden a fomentar programas con capas densas que destruyen la transparencia. [ 46] Raymond compara esto desfavorablemente con el enfoque adoptado con Unix y el lenguaje de programación C. [46]

El " principio abierto/cerrado " defiende que las clases y funciones "deberían estar abiertas a la extensión, pero cerradas a la modificación". Luca Cardelli ha afirmado que los lenguajes OOP tienen "propiedades de modularidad extremadamente pobres con respecto a la extensión y modificación de clases", y tienden a ser extremadamente complejos. [41] Este último punto es reiterado por Joe Armstrong , el principal inventor de Erlang , quien es citado diciendo: [42]

El problema con los lenguajes orientados a objetos es que tienen todo este entorno implícito que llevan consigo. Querías un plátano, pero lo que conseguiste fue un gorila sosteniendo el plátano y toda la jungla.

Leo Brodie ha sugerido una conexión entre la naturaleza independiente de los objetos y una tendencia a duplicar el código [47] en violación del principio de no repetirse [48] del desarrollo de software.

Polimorfismo

La subtipificación , una forma de polimorfismo , se produce cuando el código de llamada puede ser independiente de la clase en la jerarquía admitida en la que opera: la clase principal o una de sus descendientes. Mientras tanto, el mismo nombre de operación entre objetos en una jerarquía de herencia puede comportarse de manera diferente.

Por ejemplo, los objetos del tipo Circle y Square se derivan de una clase común llamada Shape. La función Draw para cada tipo de Shape implementa lo necesario para dibujarse a sí misma, mientras que el código de llamada puede permanecer indiferente al tipo particular de Shape que se está dibujando.

Este es otro tipo de abstracción que simplifica el código externo a la jerarquía de clases y permite una fuerte separación de preocupaciones .

Recursión abierta

Una característica común de los objetos es que los métodos están asociados a ellos y pueden acceder y modificar los campos de datos del objeto. En este tipo de programación orientada a objetos, normalmente hay un nombre especial como thiso selfque se utiliza para hacer referencia al objeto actual. En los lenguajes que admiten la recursión abierta , los métodos de objeto pueden llamar a otros métodos en el mismo objeto (incluidos ellos mismos) utilizando este nombre. Esta variable está enlazada en tiempo real ; permite que un método definido en una clase invoque otro método que se define más tarde, en alguna subclase de la misma.

Lenguajes OOP

Simula (1967) es generalmente aceptado como el primer lenguaje con las características primarias de un lenguaje orientado a objetos. Fue creado para realizar programas de simulación , en los que lo que se dio en llamar objetos eran la representación de información más importante. Smalltalk (1972 a 1980) es otro ejemplo temprano y con el que se desarrolló gran parte de la teoría de la POO. En cuanto al grado de orientación a objetos, se pueden hacer las siguientes distinciones:

Popularidad y recepción

Gráfico del índice de popularidad del lenguaje de programación TIOBE de 2002 a 2023. En la década de 2000, el lenguaje orientado a objetos Java (naranja) y el lenguaje procedimental C (azul oscuro) compitieron por la primera posición.

Muchos lenguajes ampliamente utilizados, como C++, Java y Python, proporcionan características orientadas a objetos. Aunque en el pasado la programación orientada a objetos era ampliamente aceptada, [50] más recientemente los ensayos que critican la programación orientada a objetos y recomiendan evitar estas características (generalmente a favor de la programación funcional ) han sido muy populares en la comunidad de desarrolladores. [51] Paul Graham ha sugerido que la popularidad de la programación orientada a objetos dentro de las grandes empresas se debe a "grupos grandes (y frecuentemente cambiantes) de programadores mediocres". Según Graham, la disciplina impuesta por la programación orientada a objetos evita que cualquier programador "haga demasiado daño". [52] Eric S. Raymond , un programador de Unix y defensor del software de código abierto , ha criticado las afirmaciones que presentan la programación orientada a objetos como la "única solución verdadera". [46]

Richard Feldman sostiene que estos lenguajes pueden haber mejorado su modularidad al añadir características OO, pero se hicieron populares por razones distintas a la de estar orientados a objetos. [53] En un artículo, Lawrence Krubner afirmó que, en comparación con otros lenguajes (dialectos LISP, lenguajes funcionales, etc.), los lenguajes OOP no tienen puntos fuertes únicos e imponen una gran carga de complejidad innecesaria. [54] Un estudio de Potok et al. no ha demostrado ninguna diferencia significativa en productividad entre los enfoques OOP y procedimentales. [55] Luca Cardelli ha afirmado que el código OOP es "intrínsecamente menos eficiente" que el código procedimental y que el OOP puede tardar más en compilarse. [41]

POO en lenguajes dinámicos

En los últimos años, la programación orientada a objetos se ha vuelto especialmente popular en los lenguajes de programación dinámicos . Python , PowerShell , Ruby y Groovy son lenguajes dinámicos construidos sobre principios de OOP, mientras que Perl y PHP han ido añadiendo características orientadas a objetos desde Perl 5 y PHP 4, y ColdFusion desde la versión 6.

El modelo de objetos de documento de los documentos HTML , XHTML y XML en Internet tiene enlaces al popular lenguaje JavaScript / ECMAScript . JavaScript es quizás el lenguaje de programación basado en prototipos más conocido , que emplea la clonación a partir de prototipos en lugar de heredar de una clase (a diferencia de la programación basada en clases ). Otro lenguaje de programación que adopta este enfoque es Lua .

OOP en un protocolo de red

Los mensajes que fluyen entre computadoras para solicitar servicios en un entorno cliente-servidor pueden diseñarse como linealizaciones de objetos definidos por objetos de clase conocidos tanto por el cliente como por el servidor. Por ejemplo, un objeto linealizado simple constaría de un campo de longitud, un punto de código que identifica la clase y un valor de datos. Un ejemplo más complejo sería un comando que constaría de la longitud y el punto de código del comando y valores que constarían de objetos linealizados que representan los parámetros del comando. Cada uno de estos comandos debe ser dirigido por el servidor a un objeto cuya clase (o superclase) reconozca el comando y pueda proporcionar el servicio solicitado. Los clientes y servidores se modelan mejor como estructuras complejas orientadas a objetos. La Arquitectura de Gestión de Datos Distribuidos (DDM) adoptó este enfoque y utilizó objetos de clase para definir objetos en cuatro niveles de una jerarquía formal:

La versión inicial de DDM definía los servicios de archivos distribuidos. Posteriormente se amplió para convertirse en la base de la arquitectura de bases de datos relacionales distribuidas (DRDA).

Patrones de diseño

Una forma de abordar los desafíos del diseño orientado a objetos es mediante patrones de diseño , que son patrones de solución para problemas comunes en el diseño de software. Algunos de estos problemas comunes tienen implicaciones y soluciones específicas para el desarrollo orientado a objetos.

Patrones de objetos

Los siguientes son patrones de diseño de software notables para objetos OOP. [56]

Como ejemplo de un antipatrón de objeto , el objeto Dios sabe o hace demasiado.

Herencia y subtipificación conductual

Es intuitivo asumir que la herencia crea una relación semántica " es un ", y por lo tanto inferir que los objetos instanciados de subclases siempre se pueden usar de manera segura en lugar de los instanciados de la superclase. Esta intuición es, lamentablemente, falsa en la mayoría de los lenguajes OOP, en particular en todos aquellos que permiten objetos mutables . El polimorfismo de subtipos tal como lo aplica el verificador de tipos en lenguajes OOP (con objetos mutables) no puede garantizar la subtipificación conductual en ningún contexto. La subtipificación conductual es indecidible en general, por lo que no puede implementarse mediante un programa (compilador). Las jerarquías de clases u objetos deben diseñarse cuidadosamente, considerando posibles usos incorrectos que no se pueden detectar sintácticamente. Este problema se conoce como el principio de sustitución de Liskov .

Patrones de diseño de la pandilla de los cuatro

Design Patterns: Elements of Reutilizable Object-Oriented Software es un influyente libro publicado en 1994 por Erich Gamma , Richard Helm , Ralph Johnson y John Vlissides , a los que a menudo se hace referencia humorísticamente como la "Banda de los Cuatro". Además de explorar las capacidades y los problemas de la programación orientada a objetos, describe 23 problemas de programación comunes y patrones para resolverlos.

El libro describe los siguientes patrones:

Orientación a objetos y bases de datos

Tanto la programación orientada a objetos como los sistemas de gestión de bases de datos relacionales (RDBMS) son extremadamente comunes en el software actual . Dado que las bases de datos relacionales no almacenan objetos directamente (aunque algunos RDBMS tienen características orientadas a objetos para aproximarse a esto), existe una necesidad general de unir los dos mundos. El problema de unir los accesos de la programación orientada a objetos y los patrones de datos con las bases de datos relacionales se conoce como desajuste de impedancia objeto-relacional . Hay algunos enfoques para hacer frente a este problema, pero no hay una solución general sin desventajas. [57] Uno de los enfoques más comunes es el mapeo objeto-relacional , como se encuentra en lenguajes IDE como Visual FoxPro y bibliotecas como Java Data Objects y Ruby on Rails ' ActiveRecord.

También existen bases de datos de objetos que pueden utilizarse para reemplazar a los RDBMS, pero no han tenido tanto éxito técnico ni comercial como los RDBMS.

Modelado y relaciones del mundo real

La programación orientada a objetos se puede utilizar para asociar objetos y procesos del mundo real con sus contrapartes digitales. Sin embargo, no todo el mundo está de acuerdo en que la programación orientada a objetos facilite el mapeo directo del mundo real o en que el mapeo del mundo real sea siquiera un objetivo digno; Bertrand Meyer sostiene en Object-Oriented Software Construction que un programa no es un modelo del mundo sino un modelo de alguna parte del mundo; "La realidad es un primo dos veces alejado". [58] Al mismo tiempo, se han señalado algunas limitaciones principales de la programación orientada a objetos. [59] Por ejemplo, el problema círculo-elipse es difícil de manejar utilizando el concepto de herencia de la programación orientada a objetos .

Sin embargo, Niklaus Wirth (quien popularizó el adagio ahora conocido como la ley de Wirth : "El software se vuelve más lento más rápidamente de lo que el hardware se vuelve más rápido") dijo de la POO en su artículo, "Buenas ideas a través del espejo", "Este paradigma refleja de cerca la estructura de los sistemas en el mundo real y, por lo tanto, es muy adecuado para modelar sistemas complejos con comportamiento complejo" [60] (contraste con el principio KISS ).

Steve Yegge y otros observaron que los lenguajes naturales carecen del enfoque OOP de priorizar estrictamente las cosas (objetos/ sustantivos ) antes que las acciones (métodos/ verbos ). [61] Este problema puede hacer que la OOP sufra soluciones más complicadas que la programación procedimental. [62]

OOP y flujo de control

La programación orientada a objetos se desarrolló para aumentar la reutilización y la capacidad de mantenimiento del código fuente. [63] La representación transparente del flujo de control no tenía prioridad y estaba destinada a ser manejada por un compilador. Con la creciente relevancia del hardware paralelo y la codificación multiproceso , el desarrollo de un flujo de control transparente se vuelve más importante, algo difícil de lograr con la programación orientada a objetos. [64] [65] [66] [67]

Diseño basado en responsabilidades versus diseño basado en datos

El diseño basado en la responsabilidad define las clases en términos de un contrato, es decir, una clase debe definirse en torno a una responsabilidad y la información que comparte. Wirfs-Brock y Wilkerson contrastan esto con el diseño basado en datos , en el que las clases se definen en torno a las estructuras de datos que deben contenerse. Los autores sostienen que el diseño basado en la responsabilidad es preferible.

Pautas SOLID y GRASP

SOLID es un mnemotécnico inventado por Michael Feathers que detalla cinco principios de diseño de ingeniería de software:

GRASP (Patrones de software de asignación de responsabilidad general) es otro conjunto de pautas defendidas por Craig Larman .

Semántica formal

Los objetos son las entidades de tiempo de ejecución en un sistema orientado a objetos. Pueden representar una persona, un lugar, una cuenta bancaria, una tabla de datos o cualquier elemento que el programa tenga que manejar.

Se han hecho varios intentos de formalizar los conceptos utilizados en la programación orientada a objetos. Los siguientes conceptos y construcciones se han utilizado como interpretaciones de los conceptos de programación orientada a objetos:

Los intentos de encontrar una definición o teoría de consenso detrás de los objetos no han tenido mucho éxito (sin embargo, véase Abadi & Cardelli, A Theory of Objects [69] para definiciones formales de muchos conceptos y construcciones de OOP), y a menudo divergen ampliamente. Por ejemplo, algunas definiciones se centran en las actividades mentales y otras en la estructuración de programas. Una de las definiciones más simples es que OOP es el acto de usar estructuras de datos o matrices de "mapas" que pueden contener funciones y punteros a otros mapas, todo con algo de azúcar sintáctica y de alcance por encima. La herencia se puede realizar clonando los mapas (a veces llamado "creación de prototipos").

Sistemas

Lenguajes de modelado

Véase también

Referencias

  1. ^ abcd "Dr. Alan Kay sobre el significado de "programación orientada a objetos"". 2003 . Consultado el 11 de febrero de 2010 .
  2. ^ Kindler, E.; Krivy, I. (2011). "Simulación orientada a objetos de sistemas con control sofisticado". Revista Internacional de Sistemas Generales . 40 (3): 313–343. doi :10.1080/03081079.2010.539975.
  3. ^ Lewis, John; Loftus, William (2008). Fundamentos del diseño de programación de soluciones de software Java, sexta edición . Pearson Education Inc. ISBN 978-0-321-53205-3., sección 1.6 "Programación Orientada a Objetos"
  4. ^ ab Bloch 2018, págs. xi-xii, Prólogo.
  5. ^ McCarthy, J.; Brayton, R.; Edwards, D.; Fox, P .; Hodes, L .; Luckham, D .; Maling, K.; Park, D .; Russell, S. (marzo de 1969). "LISP I Programmers Manual" (PDF) . Computation Center and Research Laboratory of Electronics . Boston , Massachusetts : Artificial Intelligence Group, MIT Computation Center and Research Laboratory: 88f. Archivado desde el original (PDF) el 17 de julio de 2010. En el dialecto local del MIT, las listas de asociación [de símbolos atómicos] también se denominan "listas de propiedades", y los símbolos atómicos a veces se denominan "objetos".
  6. ^ McCarthy, John ; Abrahams, Paul W.; Edwards, Daniel J.; Hart, swapnil d.; Levin, Michael I. (1962). Manual del programador de LISP 1.5. MIT Press . pág. 105. ISBN 978-0-262-13011-0Objeto : sinónimo de símbolo atómico
  7. ^ Ivan E. Sutherland (mayo de 1963). Sketchpad: un sistema de comunicación gráfica hombre-máquina . AFIPS '63 (primavera): Actas de la Conferencia conjunta de informática de primavera del 21 al 23 de mayo de 1963. AFIPS Press. págs. 329–346. doi : 10.1145/1461551.1461591 .
  8. ^ por Kristen Nygaard ; Ole-Johan Dahl (1 de agosto de 1978). "El desarrollo de los lenguajes SIMULA". ACM SIGPLAN Notices . 13 (8): 245–272. doi : 10.1145/960118.808391 .
  9. ^ Ross, Doug. "El primer lenguaje de ingeniería de software". Cronología del laboratorio LCS/AI . Laboratorio de Ciencias de la Computación e Inteligencia Artificial del MIT . Consultado el 13 de mayo de 2010 .
  10. ^ ab Holmevik, Jan Rune (invierno de 1994). «Compiling Simula: A historical study of technical genesis» (PDF) . IEEE Annals of the History of Computing . 16 (4): 25–37. doi :10.1109/85.329756. S2CID  18148999. Archivado desde el original (PDF) el 30 de agosto de 2017. Consultado el 3 de marzo de 2018 .
  11. ^ Butcher, Paul (30 de junio de 2014). Siete modelos de concurrencia en siete semanas: cuando los subprocesos se deshacen. Pragmatic Bookshelf. p. 204. ISBN 978-1-68050-466-8.
  12. ^ Jones, Anita K.; Liskov, Barbara H. (abril de 1976). Una herramienta de control de acceso para lenguajes de programación (PDF) (informe técnico). MIT. CSG Memo 137.
  13. ^ de Bertrand Meyer (2009). Touch of Class: Aprendiendo a programar bien con objetos y contratos . Springer Science & Business Media. p. 329. Bibcode :2009tclp.book.....M. ISBN 978-3-540-92144-8.
  14. ^ Alan C. Kay (marzo de 1993). "La historia temprana de Smalltalk". Avisos SIGPLAN de la ACM . 28 (3): 69–95. doi : 10.1145/155360.155364 .
  15. ^ Moon, David A. (junio de 1986). "Object-Oriented Programming with Flavors" (PDF) . Actas de congresos sobre lenguajes y aplicaciones de sistemas de programación orientados a objetos . OOPSLA '86. págs. 1–8. doi :10.1145/28697.28698. ISBN 978-0-89791-204-4. S2CID  17150741 . Consultado el 17 de marzo de 2022 .
  16. ^ "Presentación del zoológico Smalltalk". CHM . 17 de diciembre de 2020.
  17. ^ Bobrow, DG; Stefik, M. J (1982). LOOPS: programación orientada a datos y objetos para Interlisp (PDF) . Conferencia Europea de IA.
  18. ^ Meyer 1997.
  19. ^ 1995 (junio) Visual FoxPro 3.0, FoxPro evoluciona de un lenguaje procedimental a un lenguaje orientado a objetos. Visual FoxPro 3.0 introduce un contenedor de base de datos, capacidades cliente/servidor sin fisuras, compatibilidad con tecnologías ActiveX y automatización OLE y compatibilidad con valores nulos. Resumen de las versiones de Fox
  20. ^ Guía de revisores de Visual FoxPro 3.0 de 1995: DFpug.de
  21. ^ Khurana, Rohit (1 de noviembre de 2009). Programación orientada a objetos con C++, 1E. Vikas Publishing House Pvt Limited. ISBN 978-81-259-2532-3.
  22. ^ Deborah J. Armstrong. The Quarks of Object-Oriented Development . Un estudio de casi 40 años de literatura informática identificó varios conceptos fundamentales que se encuentran en la gran mayoría de las definiciones de programación orientada a objetos, en orden descendente de popularidad: herencia, objeto, clase, encapsulación, método, paso de mensajes, polimorfismo y abstracción.
  23. ^ John C. Mitchell , Conceptos en lenguajes de programación , Cambridge University Press, 2003, ISBN 0-521-78098-5 , p.278. Listas: distribución dinámica, abstracción, polimorfismo de subtipos y herencia. 
  24. ^ Michael Lee Scott, Pragmática del lenguaje de programación , Edición 2, Morgan Kaufmann, 2006, ISBN 0-12-633951-1 , pág. 470. Encapsulación de listas, herencia y despacho dinámico. 
  25. ^ Pierce, Benjamin (2002). Tipos y lenguajes de programación . MIT Press. ISBN 978-0-262-16209-8., sección 18.1 "¿Qué es la programación orientada a objetos?" Listas: Despacho dinámico, encapsulamiento o métodos múltiples (despacho múltiple), polimorfismo de subtipos, herencia o delegación, recursión abierta ("this"/"self")
  26. ^ CJ Date, Introducción a los sistemas de bases de datos, 6.ª ed., página 650
  27. ^ Booch, Grady (1986). Ingeniería de software con Ada. Addison Wesley. pág. 220. ISBN 978-0-8053-0608-8Quizás la mayor fortaleza de un enfoque de desarrollo orientado a objetos es que ofrece un mecanismo que captura un modelo del mundo real.
  28. ^ CJ Date, Hugh Darwen. Fundación para los sistemas de bases de datos del futuro: el tercer manifiesto (segunda edición)
  29. ^ ab Stepanov, Alexander . "STLport: una entrevista con A. Stepanov" . Consultado el 21 de abril de 2010 .
  30. ^ por Rich Hickey, orador principal de la JVM Languages ​​Summit 2009, ¿Ya llegamos?, noviembre de 2009.
  31. ^ Pike, Rob (25 de junio de 2012). "Menos es exponencialmente más" . Consultado el 1 de octubre de 2016 .
  32. ^ "Stevey's Blog Rants: Execution in the Kingdom of Nouns" (Despotricando en el blog de Stevey: Ejecución en el reino de los sustantivos) . Consultado el 20 de mayo de 2020 .
  33. ^ Bloch 2018, p. 19, Capítulo §2 Artículo 4 Hacer cumplir la no instanciabilidad con un constructor privado.
  34. ^ Dony, C; Malenfant, J; Bardon, D (1999). "Clasificación de lenguajes de programación basados ​​en prototipos" (PDF) . Programación basada en prototipos: conceptos, lenguajes y aplicaciones . Singapur Berlín Heidelberg: Springer. ISBN 9789814021258.
  35. ^ "¿Go es un lenguaje orientado a objetos?" . Consultado el 13 de abril de 2019 . Aunque Go tiene tipos y métodos y permite un estilo de programación orientado a objetos, no existe una jerarquía de tipos.
  36. ^ Stroustrup, Bjarne (2015). Programación orientada a objetos sin herencia (charla invitada). 29.ª Conferencia Europea sobre Programación Orientada a Objetos (ECOOP 2015). 1:34. doi : 10.4230/LIPIcs.ECOOP.2015.1 .
  37. ^ Pike, Rob (14 de noviembre de 2012). «Hace unos años vi esta página». Archivado desde el original el 14 de agosto de 2018. Consultado el 1 de octubre de 2016 .
  38. ^ Pike, Rob (2 de marzo de 2004). "[9fans] Re: Hilos: Coser insignias de honor en un núcleo". comp.os.plan9 (Lista de correo) . Consultado el 17 de noviembre de 2016 .
  39. ^ "Principios SOLID del tío Bob". YouTube . 2 de agosto de 2018.
  40. ^ Jacobsen, Ivar; Magnus Christerson; Patrik Jonsson; Gunnar Overgaard (1992). Ingeniería de Software Orientada a Objetos. Prensa Addison-Wesley ACM. págs. 43–69. ISBN 978-0-201-54435-0.
  41. ^ abc Cardelli, Luca (1996). "Malas propiedades de ingeniería de los lenguajes orientados a objetos". ACM Comput. Surv . 28 (4es): 150–es. doi :10.1145/242224.242415. ISSN  0360-0300. S2CID  12105785. Consultado el 21 de abril de 2010 .
  42. ^ ab Armstrong, Joe. En Coders at Work: Reflections on the Craft of Programming. Peter Seibel, ed. Codersatwork.com Archivado el 5 de marzo de 2010 en Wayback Machine . Consultado el 13 de noviembre de 2009.
  43. ^ ab Bloch 2018, pp. 73–77, Capítulo §4 Elemento 15 Minimizar la accesibilidad de clases y miembros.
  44. ^ "¿Qué es la programación orientada a objetos (POO) en palabras sencillas? – Software Geek Bytes". 5 de enero de 2023. Consultado el 17 de enero de 2023 .
  45. ^ Cardelli, Luca; Wegner, Peter (10 de diciembre de 1985). "Sobre la comprensión de los tipos, la abstracción de datos y el polimorfismo". ACM Computing Surveys . 17 (4): 471–523. doi : 10.1145/6041.6042 . ISSN  0360-0300.
  46. ^ abc Eric S. Raymond (2003). "El arte de la programación Unix: Unix y lenguajes orientados a objetos" . Consultado el 6 de agosto de 2014 .
  47. ^ Brodie, Leo (1984). Thinking Forth (PDF) . pp. 92–93 . Consultado el 4 de mayo de 2018 .
  48. ^ Hunt, Andrew. "No te repitas". Categoría Programación extrema . Consultado el 4 de mayo de 2018 .
  49. ^ "El lenguaje de programación Emerald". 26 de febrero de 2011.
  50. ^ Brucker, Achim D.; Wolff, Burkhart (2008). "Universos extensibles para modelos de datos orientados a objetos". ECOOP 2008 – Programación orientada a objetos . Apuntes de clase en informática. Vol. 5142. págs. 438–462. doi :10.1007/978-3-540-70592-5_19. ISBN 978-3-540-70591-8La programación orientada a objetos es un paradigma de programación ampliamente aceptado .
  51. ^ Cassel, David (21 de agosto de 2019). "¿Por qué tantos desarrolladores odian la programación orientada a objetos?". The New Stack .
  52. ^ Graham, Paul . "Por qué ARC no está especialmente orientado a objetos". PaulGraham.com . Consultado el 13 de noviembre de 2009 .
  53. ^ Feldman, Richard (30 de septiembre de 2019). "¿Por qué la programación funcional no es la norma?". YouTube .
  54. ^ Krubner, Lawrence. "La programación orientada a objetos es un desastre costoso que debe terminar". smashcompany.com. Archivado desde el original el 14 de octubre de 2014. Consultado el 14 de octubre de 2014 .
  55. ^ Potok, Thomas; Mladen Vouk; Andy Rindos (1999). "Análisis de productividad de software orientado a objetos desarrollado en un entorno comercial" (PDF) . Software: práctica y experiencia . 29 (10): 833–847. doi :10.1002/(SICI)1097-024X(199908)29:10<833::AID-SPE258>3.0.CO;2-P. S2CID  57865731. Consultado el 21 de abril de 2010 .
  56. ^ Martin, Robert C. "Principios de diseño y patrones de diseño" (PDF) . Archivado desde el original (PDF) el 6 de septiembre de 2015. Consultado el 28 de abril de 2017 .
  57. ^ Neward, Ted (26 de junio de 2006). "El Vietnam de la informática". La interoperabilidad es una realidad. Archivado desde el original el 4 de julio de 2006. Consultado el 2 de junio de 2010 .
  58. ^ Meyer 1997, pág. 230.
  59. ^ M.Trofimov, OOOP – La tercera solución "O": OOP abierta. Primera clase, OMG , 1993, vol. 3, número 3, pág. 14.
  60. ^ Niklaus Wirth (23 de enero de 2006). "Buenas ideas, a través del espejo" (PDF) . IEEE Computer . Artículo de portada. 39 (1): 28–39. doi :10.1109/MC.2006.20. S2CID  6582369. Archivado desde el original (PDF) el 12 de octubre de 2016.
  61. ^ Yegge, Steve (30 de marzo de 2006). "Ejecución en el reino de los sustantivos". steve-yegge.blogspot.com . Consultado el 3 de julio de 2010 .
  62. ^ Boronczyk, Timothy (11 de junio de 2009). "What's Wrong with OOP" (¿Qué está mal con la programación orientada a objetos?). zaemis.blogspot.com . Consultado el 3 de julio de 2010 .
  63. ^ Ambler, Scott (1 de enero de 1998). "Una mirada realista a la reutilización orientada a objetos". drdobbs.com . Consultado el 4 de julio de 2010 .
  64. ^ Shelly, Asaf (22 de agosto de 2008). "Flaws of Object Oriented Modeling". Intel Software Network . Consultado el 4 de julio de 2010 .
  65. ^ James, Justin (1 de octubre de 2007). "Multithreading es un verbo, no un sustantivo". techrepublic.com. Archivado desde el original el 10 de octubre de 2007. Consultado el 4 de julio de 2010 .
  66. ^ Shelly, Asaf (22 de agosto de 2008). "CÓMO: Programación multinúcleo (multiprocesamiento) Directrices de diseño de clases de Visual C++, funciones miembro". support.microsoft.com . Consultado el 4 de julio de 2010 .
  67. ^ Robert Harper (17 de abril de 2011). "Algunas reflexiones sobre la enseñanza de la planificación familiar". Blog de tipo existencial . Consultado el 5 de diciembre de 2011 .
  68. ^ Poll, Erik. "Subtipificación y herencia de tipos de datos categóricos" (PDF) . Consultado el 5 de junio de 2011 .
  69. ^ Abadi, Martin ; Cardelli, Luca (1996). Una teoría de los objetos. Springer-Verlag New York, Inc. ISBN 978-0-387-94775-4. Recuperado el 21 de abril de 2010 .

Lectura adicional

Enlaces externos

Véase también