lunes, 24 de abril de 2017

Diferencias entre Abstracción y Encapsulación en Java. POO

Tanto la Abstracción como la Encapsulación son dos de los cuatros conceptos básicos de la Programación Orientada a Objetos (POO) con los cuales puedes modelar las cosas del mundo real en objetos y puedas implementarlas en tu programa y código. Muchos principiantes tienden a confundir estos términos por lo similar que pueden llegar a lucir. Si tu le preguntas a alguien ¿que es la Abstracción?, esa persona te responderá que es un concepto de la POO que se centra en la información pertinente ocultando detalles innecesarios, y cuando preguntas acerca de la Encapsulación, muchos te responden que es otro concepto de la POO el cual oculta datos del mundo exterior. Las definiciones no son erróneas ya que tanto la Abstracción como la Encapsulación ocultan algo, pero la diferencia clave esta en la intención.

La abstracción oculta la complejidad para dar una imagen mas abstracta, mientras que la encapsulación oculta el trabajo interno para que puedas cambiarlo posteriormente. En otras palabras, la Abstracción oculta detalles a nivel de diseño, mientras que la Encapsulación oculta detalles a nivel de implementación.

Por ejemplo, cuando describes un objeto por primera vez, hablas en términos mas abstractos, como: "Vehículo que se puede mover", no dices cómo se moverá el vehículo, si se moverá usando neumáticos, si volará o si navegará. Solo se mueve. A esto llamamos Abstracción. Estamos hablando de una de las cosas mas esenciales, y es que esta en movimiento, en vez de centrarse en detalles sobre cómo se mueve, si por tierra, volando o por agua.

Están también los diferentes niveles de Abstracción y es una buena práctica que las clases deberían interactuar con otras clases con un mismo nivel de Abstracción o mayor nivel de Abstracción. De manera que a medida que incrementa el nivel de Abstracción, las cosas empiezan a ser cada vez mas simples, dejando a un lado los detalles.

Por otro lado, la Encapsulación trata sobre la implementación. Su único propósito es ocultar el trabajo interno de los objetos del mundo exterior para que pueda cambiarlo mas tarde sin afectar a los clientes externos.

Por ejemplo, tenemos un HashMap que permite almacenar el objeto utilizando el método put() y recuperar el objeto utilizando el método get(). Cómo HashMaps implementa este método (lee mas aquí) es un detalle interno de HashMap, el cliente solo se preocupa por almacenar los objetos y devolverlo, a él no le concierne si HashMap esta usando un arreglo, cómo esta resolviendo la colisión, si esta usando una lista o un árbol binario para almacenar el intercambio de los objetos en la memoria, etc.

Debido a la Encapsulación, tu puedes cambiar el funcionamiento interno de HashMap con facilidad sin interferir con los clientes que están usando HashMap. Por ejemplo, en Java 8, el java.util.HashMap cambia su implementación para usar un árbol binario en lugar de una lista para almacenar los objetos en el mismo lugar después de cierto punto (lee mas aquí).

El cliente no necesita hacer ningún cambio para beneficiarse de este cambio de código porque esos detalles no están expuestos a ellos. Si el cliente tuviera conocimiento de ello, es decir, que de alguna manera pudiesen tener referencia del arreglo interno del HashMap, no habría sido posible cambiar la implementación sin afectar a los demás clientes. 

Existen muchos principios de diseño basados en la Abstracción, como por ejemplo, "Codificación para interfaces después de la implementación" que ayuda a escribir código flexible en Java o C++. La idea es que una clase dependa de una interfaz, un nivel de abstracción mas alto que la clase, un un menor nivel de abstracción. Esto resulta en un código flexible que puede funcionar con cualquier implementación de la interfaz. 

Por ejemplo, si tu necesitas HashMap, tu clase debe depender de Map en lugar de HashMap. De igual forma, si tu necesitas ArrayList, asegúrate de usar la List. Afortunadamente, el tío Bob ha compartido varios principios de diseño sobre Clean Code, conocidos colectivamente como principios de diseño SOLID, que es algo que cada programador POO debe aprender y entender. 
Clean Code

Abstracción Vs. Encapsulación. 

A continuación y a modo de resumen, desglosamos por puntos las principales diferencias entre Encapsulación y Abstracción.
  1. La diferencia mas importante entre Abstracción y Encapsulación es que la Abstracción resuelve el problema en un nivel de diseño mientras que la Encapsulación lo resuelve en un nivel de implementación. 
  2. La Abstracción busca esconder detalles no deseados mientras genera detalles mas esenciales, mientras que la Encapsulación busca ocultar el código y los datos dentro de una sola unidad, es decir, una clase o un método protegen su trabajo interno de objetos externos. En otras palabras, la Abstracción solo extrae detalles comunes o generaliza cosas. 
  3. La Abstracción permite centrarse en lo que el objeto hace en lugar de como lo hace, mientras la Encapsulación busca ocultar los detalles internos o forma de trabajar de un objeto. Cuando mantienes privados los detalles internos de trabajo de un objeto, se pueden editar posteriormente por un método mejor. El libro Head First Object Oriented Analysis and Design tiene algunos ejemplos excelentes de estos conceptos de POO, le sugiero que lean este libro al menos una vez para revisar los fundamentos de la POO. 
     Head First Object Oriented Analysis and Design
  4. El enfoque de la abstracción es externo, por ejemplo: Desplazamiento del vehículo. Mientras que la encapsulación se ocupa del trabajo interno, por ejemplo: como se mueve exactamente el vehículo. 
  5. En Java, la Abstracción esta apoyada por el uso de interfaces y clases abstractas mientras que la Encapsulación esta soportada por el uso de los modificadores de accesos: public, private and protected. 
En la siguiente tabla se destacan las principales diferencias entre la Abstracción y la Encapsulación en Programación Orientada a Objetos:
Cuadro comparativo. Abstracción Vs. Encapsulación.
Esto es todo acerca de las diferencias entre la Abstracción y la Encapsulación en Java y POO. Yo entiendo, ambos parecen muy similares, pero como he dicho son conceptos totalmente diferentes. Solo recuerda que la Abstracción resuelve los problemas en el nivel de diseño mientras la Encapsulación los resuelve en el nivel de implementación. Ambos son muy importantes para un programador POO pero algunas veces resulta difícil de explicar.

Como dije anteriormente, la mejor manera de aprender y volverse un master de la Programación Orientada a Objetos es escribiendo código y leyendo el código de otros. Cuanto mas se exponen al código, mas se dan cuenta de cómo funcionan estos conceptos en la práctica. Hay varios principios de diseño que se basan en términos de abstracción, por ejemplo, codificación de interfaz en lugar de implementación, el cual permite escribir codigo flexible. 

Otras entradas sobre POO que podrían gustarte: 
  • Diferencias entre Clase y Objeto en Java y POO (haz clic aquí).
  • Diferencias entre Herencia y Polimorfismo en Java (Pronto traducido aquí).
  • Diferencias entre Agregación, Composición y Asociación en POO (Pronto traducido aquí).
  • Diferencias entre patrones de diseño de Estado y Estrategia (Pronto traducido aquí).
  • ¿Que es el Polimorfismo?¿Sobrecarga o Anulación? (Pronto traducido aquí).
  • ¿Cual es la diferencia entre Sobrecarga y Anulación en POO? (Pronto traducido aquí).
  • Diferencias entre instancia y objetos en Java (Pronto traducido aquí).
  • ¿Cual es la diferencia entre un descubrimiento estático y dinámico en Java? (Pronto traducido aquí).

Gracias por leer este articulo, si de verdad te gusto, no dejes de compartirlo con tus amigos y colegas. Si tienes alguna pregunta o sugerencia, por favor déjala en los comentarios. Y si quieres saber mas sobre conceptos de POO, principios de diseño SOLID y  aplicación de los conceptos de POO en la vida real, no dejes de leer Clean Code

***El Artículo fue obtenido de JavaRevisited y fue modificado ligeramente para su traducción. Para revisar el contenido original dar clic aquí.

    Choose :
  • OR
  • To comment
No hay comentarios:
Write comentarios