Class Encapsulation / Encapsulamiento de Clases - Coding Basics #13

Words
1926
Reading
9 min
Listen
Play
3y

self.__newPost = newPost

TitleImage.png

Shoutout to Stackify

HiveDivider.png

In this article you'll find:

  • Introduction
  • What is encapsulation?
  • Access Modifiers
  • Public Members
  • Private Members
  • Protected Members
  • Getters and Setters

HiveDivider.png

So far we have seen two very important properties of object-oriented programming: Inheritance and polymorphism. With one, we can create classes that can use the attributes and methods of another class and with the other we can use methods with the same name in different classes.

However, another key concept in Python is Encapsulation, with which we can hide and protect the information of our classes from malicious users.

If you want to learn how to have secret information in your classes and how to reveal "only what they need to know", This article will be excellent for you.

Without further ado:

Let's get started!

.

HiveDivider.png

What is Encapsulation?

python_data_hiding.jpg

Shoutout to PYnative

Encapsulation refers to the grouping of methods, attributes and information within a single unit.

The most obvious example is that of classes, where we have attributes and methods that we create within them. Seeing it in the following image:

image.png

So, understanding its basic operation is simple, but the real potential is hidden in its Access Modifiers. Let's see it.

HiveDivider.png

Access Modifiers

Encapsulation in Python OOP.jpg

Shoutout to Geospatial Solutions Expert

Let's say we create a class with some attributes and two methods to show us these attributes:

class EncapsulationTest:
     def __init__(self, param1, param2):
         self.param1 = param1
         self.param2 = param2

     def show_param1(self):
         return(self.param1)

Now, so that the encapsulation is carried out, we must hide some of these data to the external access of the class, or at least make sure that it only shows the information without modifying it to avoid changes generated to this one. For this, we use the concept of Data Members, which simply refers to the attributes of the class.

This is where access modifiers come in, where for languages such as Java and C++ these can be declared when creating the class attributes. However, in Python, we use underscores (_) to determine if a member is part of the following categories:

  • Public Member
  • Private Member
  • Protected Member

Now, what does it mean if a member is public, private or protected? Let's see:

HiveDivider.png

Public Members

46.PNG

Shoutout to Learn Electronics with Me

So far, all class member attributes we have created have been public. This is because by default, Python makes them public. But what does it mean that a member is public?

A public member is a variable or attribute that can be accessed inside or outside the class. If we take into account the class defined above, we will see that when we look at init:

class EncapsulationTest:
     def __init__(self, param1, param2):
         self.param1 = param1
         self.param2 = param2

We have two public members in param1 and param2. If we want to access these, we just create an EncapsulationTest class object and place the attribute name:

obj1 = EncapsulationTest('param1','param2')
print(obj1.param1)
print(obj1.param2)
>>> 
param1
param2

So, we can check that because they can be entered from outside the class, these are public members.

HiveDivider.png

Private Members

privatemethod.png

Shoutout to Gaurav Patil from Medium

The opposite of a public member, private members can only be accessed from inside the class, which means that if we try to do the same as in the previous example, we will get an error message. If we want to make a member private, just place __ before the attribute name. Creating a third attribute for the EncapsulationTest class:

class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self.__param3 = param3 

Thus, testing if it can be accessed:

obj3 = EncapsulationTest('param1','param2','param3')
print(obj3.__param3)

>>>>AttributeError: 'EncapsulationTest' object has no attribute '__param3'.

So we confirm that it is a private member. For those cases where we really want to access a private attribute, there are two solutions:

  • Create a method inside the same class that allows us to access the member (this since the operation would be performed inside the class):
class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self.__param3 = param3 

    def access_param3(self):
        return self.__param3

obj3 = EncapsulationTest('param1','param2','param3')
print(obj3.show_param3())

>>> param3
  • Use name mangling, where, when searching for the attribute from an object, we must precede this with the class name preceded by an underscore and followed by two underscores. Thus:
class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self.__param3 = param3 

obj3 = EncapsulationTest('param1','param2','param3')
print(obj3._EncapsulationTest__param3)

>>> param3

HiveDivider.png

Protected Members

BoardInfinity.png

Shoutout to Board Infinity

One of the problems of private members can be found when working with inheritance (More about this in a previous article), where if we try to access the private member of the parent class from the child class, we will get an error. For this, we use protected members, which can only be accessed from:

  • Inside the class
  • Inside a child class (that has inherited the attributes of the original class).

So, if we were to create a child class for EncapsulationTest and inherit all the attributes of EncapsulationTest through the init:

 class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self._param3 = param3 

class EncapsulationTest2(EncapsulationTest):
    def __init__(self, param1, param2, param3):
        EncapsulationTest.__init__(self,param1,param2,param3).

Now, if we create a method inside EncapsulationTest2 that accesses _param3:

class EncapsulationTest2(EncapsulationTest):
    def __init__(self, param1, param2, param3):
        EncapsulationTest.__init__(self,param1,param2,param3).

    def show_param3(self):
        return self._param3

obj3 = EncapsulationTest2(1,2,3)
print(obj3.show_param3())

>>>3

We will see that we can access without problem.

HiveDivider.png

Getters and Setters

RealPythonGetterSetter.webp

Shoutout to Real Python

It is good practice in Python to use Getters and Setters to ensure that the encapsulation is carried out. These implemented are methods that we create inside the class to access (In the case of getter) or modify the value of a private or protected member (In the case of setter). For example, if we create a class for the ID, name and age of the employees of a company:

class Employees:
    def __init__(self, ID, name, age):
        self.__ID = ID
        self.__name = name
        self.age = age

If we add a getter and setter:

class Employees:
    def __init__(self, ID, name, age):
        self.__ID = ID
        self.__name = name
        self.age = age

    def get_name(self):
    return self.__name

   def set_name(self, name):
       return self.__name = name

This way, when we want to access or modify the name attribute we will only have to call the methods get_name and set_name from some object that we create. Thus, we avoid the use of direct procedures to access our private member and we limit the use to these.

HiveDivider.png

We can see that encapsulation is an excellent option for those situations where we want to hide data from our users and prevent them from being modified inappropriately.

This not only provides security and anonymity, but also allows us to make our code cleaner by separating what each member does.

After reading this article, you will master the use of encapsulation, bringing you one step closer to understanding the principles of object-oriented programming, so that you can add a new layer of complexity to your programs.

HiveDivider.png

Thank you for your support and good luck!

HiveDivider.png

@jesalmofficial.png

HiveDivider.png

self.__nuevoPost = nuevoPost

TitleImage.png

Shoutout to Stackify

HiveDivider.png

In this article you'll find:

  • Introducci贸n
  • 驴Qu茅 es el encapsulamiento?
  • Modificadores de Acceso
  • Miembros P煤blicos
  • Miembros Privados
  • Miembros Protegidos
  • Getters y Setters

HiveDivider.png

Hasta ahora hemos visto dos propiedades muy importantes de la programaci贸n orientada a objetos: La herencia y el polimorfismo. Con una, podemos crear clases que pueden usar los atributos y m茅todos de otra clase y con la otra podemos emplear m茅todos con el mismo nombre en distintas clases.

Sin embargo, otro de los conceptos clave en Python es el Encapsulamiento, con el que podremos esconder y proteger la informaci贸n de nuestras clases de usuarios malintencionados.

Si quieres aprender como tener informaci贸n secreta en tus clases y como revelar "煤nicamente lo que necesitan saber", Este art铆culo ser谩 excelente para ti.

Sin m谩s que decir:

隆Comencemos!

HiveDivider.png

驴Qu茅 es el encapsulamiento?

python_data_hiding.jpg

Shoutout to PYnative

El encapsulamiento se refiere a la agrupaci贸n de m茅todos, atributos e informaci贸n dentro de una sola unidad.

El ejemplo m谩s obvio es el de las clases, donde tenemos atributos y m茅todos que creamos dentro de estas. Vi茅ndolo en la siguiente imagen:

image.png

As铆, el entender su funcionamiento b谩sico es sencillo, m谩s el verdadero potencial se esconde en los modificadores de acceso.

HiveDivider.png

Modificadores de Acceso

Encapsulation in Python OOP.jpg

Shoutout to Geospatial Solutions Expert

Digamos que creamos una clase con algunos atributos y dos m茅todos para mostrarnos estos atributos:

class EncapsulationTest:
     def __init__(self, param1, param2):
         self.param1 = param1
         self.param2 = param2

     def show_param1(self):
         return(self.param1)

Ahora, para que la encapsulaci贸n se lleve a cabo, debemos de esconder alguno de estos datos al acceso externo de la clase, o por lo menos hacer que solo muestre la informaci贸n sin modificarla para evitar cambios generados a esta. Para esto, usamos el concepto de Miembros de Datos, que simplemente hacen referencia a los atributos de la clase.

Es aqu铆 donde se hacen presentes los modificadores de acceso, donde para lenguajes como Java y C++ estos pueden declararse al crear los atributos de la clase. Sin embargo, en Python, nos valemos del uso de underscores (_) para determinar si un miembro forma parte de las siguientes categor铆as:

  • Miembro P煤blico
  • Miembro Privado
  • Miembro Protegido

Ahora, 驴Que quiere decir si un miembro es p煤blico, privado o protegido? Veamos:

HiveDivider.png

Miembros P煤blicos

46.PNG

Shoutout to Learn Electronics with Me

Hasta ahora, todos los atributos miembros de clases que hemos creado han sido p煤blicos. Esto debido a que por defecto, Python los hace p煤blicos. Pero 驴Qu茅 quiere decir que un miembro es p煤blico?

Un miembro p煤blico es aquella variable o atributo al que se puede acceder dentro o fuera de la clase. Si tomamos en cuenta la clase definida anteriormente, veremos que al observar init:

class EncapsulationTest:
     def __init__(self, param1, param2):
         self.param1 = param1
         self.param2 = param2

Tenemos dos miembros p煤blicos en param1 y param2. Si queremos acceder a estos, solo tenemos que crear un objeto de clase EncapsulationTest y colocar el nombre del atributo:

obj1 = EncapsulationTest('param1','param2')
print(obj1.param1)
print(obj1.param2)
>>> 
param1
param2

As铆, podemos comprobar que debido a que pueden ingresarse desde fuera de la clase, estos son miembros p煤blicos.

HiveDivider.png

Miembros Privados

privatemethod.png

Shoutout to Gaurav Patil from Medium

Lo opuesto a un miembro p煤blico, los miembros privados solo pueden ser accedidos desde adentro de la clase, lo que quiere decir que si intentaramos realizar lo mismo del ejemplo anterior, nos saltar铆a un mensaje de error. Si queremos hacer que un miembro sea privado, solo basta con colocar __ antes del nombre del atributo. Creando un tercer atributo para la clase EncapsulationTest:

class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self.__param3 = param3 

As铆, probando si se puede acceder:

obj3 = EncapsulationTest('param1','param2','param3')
print(obj3.__param3)

>>>AttributeError: 'EncapsulationTest' object has no attribute '__param3'

Con lo que confirmamos que es un miembro privado. Para aquellos casos en que realmente quisieramos acceder a un atributo privado, existen dos soluciones:

  • Crear un m茅todo dentro de la misma clase que nos permita acceder al miembro (Esto ya que se estar铆a realizando la operaci贸n dentro de la clase):
class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self.__param3 = param3 

    def access_param3(self):
        return self.__param3

obj3 = EncapsulationTest('param1','param2','param3')
print(obj3.show_param3())

>>> param3
  • Usar name mangling, donde, al buscar el atributo desde un objeto, debemos de preceder esto con el nombre de la clase precedido por un underscore y sucedido por dos underscores. As铆:
class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self.__param3 = param3 

obj3 = EncapsulationTest('param1','param2','param3')
print(obj3._EncapsulationTest__param3)

>>> param3

HiveDivider.png

Miembros protegidos

BoardInfinity.png

Shoutout to Board Infinity

Uno de los problemas de los miembros privados puede ser encontrado al trabajar con herencia (M谩s sobre esto en el art铆culo previo), donde si trataramos de acceder al miembro privado de la clase padre desde la clase hija, obtendr铆amos un error. Para esto, usamos los miembros protegidos, los cuales solo pueden ser accedidos desde:

  • Adentro de la clase
  • Adentro de una clase hija (Que haya heredado los atributos de la clase original).

As铆, si crearamos una clase hija para EncapsulationTest y heredaramos todos los atributos de EncapsulationTest por medio del init:

 class EncapsulationTest:
     def __init__(self, param1, param2, param3):
         self.param1 = param1
         self.param2 = param2
    self._param3 = param3 

class EncapsulationTest2(EncapsulationTest):
    def __init__(self, param1, param2, param3):
        EncapsulationTest.__init__(self,param1,param2,param3)

Ahora, si creamos un m茅todo dentro de EncapsulationTest2 que acceda a _param3:

class EncapsulationTest2(EncapsulationTest):
    def __init__(self, param1, param2, param3):
        EncapsulationTest.__init__(self,param1,param2,param3)

    def show_param3(self):
        return self._param3

obj3 = EncapsulationTest2(1,2,3)
print(obj3.show_param3())

>>>3

Veremos que podemos acceder sin problema.

HiveDivider.png

Getters y Setters

RealPythonGetterSetter.webp

Shoutout to Real Python

Es buena pr谩ctica en Python el uso de Getters y Setters para garantizar que la encapsulaci贸n se lleve a cabo. Estos implemented son m茅todos que creamos dentro de la clase para acceder (En el caso de los getter) o modificar el valor de un miembro privado o protegido (En el caso de los setter). Por ejemplo, si crearamos una clase para el ID, nombre y edad de los empleados de una compa帽铆a:

class Employees:
    def __init__(self, ID, name, age):
        self.__ID = ID
        self.__name = name
        self.age = age

Si agregamos un getter y setter:

class Employees:
    def __init__(self, ID, name, age):
        self.__ID = ID
        self.__name = name
        self.age = age

    def get_name(self):
    return self.__name

   def set_name(self, name):
       return self.__name = name

De esta forma, cuando queremos acceder o modificar el atributo name solo tendremos que llamar a los m茅todos get_name y set_name desde alg煤n objeto que creemos. As铆, nos evitamos el uso de procedimientos directos para acceder a nuestro miembro privado y limitamos el uso a estos.

HiveDivider.png

Podemos ver que el encapsulamiento es una excelente opci贸n para aquellas situaciones donde queremos ocultar datos de nuestros usuarios y evitar que sean modificados de manera inapropiada.

Esto no solo, nos brinda seguridad y anonimidad, sino que tambi茅n permit hacer nuestro c贸digo m谩s limpio al separar lo que hace cada miembro.

Tras leer este art铆culo, dominar谩s el uso del encapsulamiento, llev谩ndote un paso m谩s cerca a la comprensi贸n de los principios de la programaci贸n orientada a objetos, de manera que a帽adas una nueva capa de complejidad a tus programas.

HiveDivider.png

隆Gracias por tu apoyo y buena suerte!

HiveDivider.png

@jesalmofficial.png

HiveDivider.png

Class Encapsulation / Encapsulamiento de Clases - Coding Basics #13 | Ecency