Como  desarrolladores de software en determinado lenguaje, siendo modesta diría que no le sacamos el provecho ni en 70% de las herramientas, novedades que estos ponen a nuestra disposición. Mucho de esto de se debe a que algunos de nosotros aprendemos las cosas según las vamos necesitando.  Esto me sucedió hace poco con Reflection.

Aunque sí había escuchado el concepto no era un tema que dominaba o conociera de todo, pues hasta el momento no me hubiese visto en un caso de uso de Reflection. A parte de leer lo que necesitaba en el momento, decidí seguir aprendiendo de este tema y así como me enamoré de Reflection. A continuación hablaremos de cómo podemos usar Reflection y las características que te harán enamorarte de esta característica.

En términos generales, reflexión(Reflection) es la capacidad que tiene un programa para observar y opcionalmente modificar su estructura de alto nivel. Por lo general, reflexión es dinámica o en tiempo de ejecución.

 

Reflection aplicada en C#

Reflection objects, son usados para obtener información del tipo en tiempo de ejecución. Las clases que permiten el acceso a la metadata de un programa en ejecución se encuentran en el namespace System.Reflection

Algunos de los usos:

  • Podemos visualizar el tipo de un objeto en tiempo en ejecución.
  • Inspeccionar los atributos de un objeto en tiempo de ejecución para cambiar el comportamiento de un método.
  • Cargar un dll y determinar si contiene la implementación de una interfaz.

 

Es importante que sepamos que tenemos dos formas de usar Reflection: dynamic reflection y static reflection.

Dynamic Reflection

Como sabemos C# es un lenguaje fuertemente tipado, poder acceder a la metadata de la aplicación es muy útil pues por medio de dynamic reflection  podemos ver los tipos en el momento de ejecución. Cada objeto tiene un método GetType() por el cual podemos obtener acceso a la metadata o al tipo del mismo. Aquí te muestro el clásico ejemplo:

Static Reflection

Reúne la data a través de la inspección de un árbol de expresiones. En lugar de usar un mágico string como en este ejemplo:

Podríamos optar en algo como esto:

En lugar de utilizar un mágico string usamos una expresión lambda(es un delegado anónimo solo que menos detallado).


Nota:

Que nuestro único exceso, sea el exceso de gratitud. Con reflection no debe ser la excepción, no todos los casos son iguales, pero debemos tomar en cuenta el precio que debemos pagar por uso de reflection: No hay una verificación en tiempo de compilación de los nombres o tipos de campos o cualquier información que esté recopilando a través de reflection.

El principal peligro con Reflection es que la flexibilidad puede escalar hasta convertirse en código desorganizado, que no se puede mantener.


Caso Personal:

Actualmente, estuve trabajando en un proyecto con un framework dinosaurio utilizando Net Framework 3.5, lo interesante del caso es que para muchas de las modificaciones se necesita heredar de una X clase que se encuentra en una DLL Y, implementar interfaces y override a esos métodos, todo miel sobre hojuelas, hasta que necesitaba una propiedad de la clase padre que fuese privada.

Y en medio de la confusión e irritación llegó Reflection a mi vida y pude obtener las propiedades que necesitaba, invocar métodos, Settear propiedades todo sin morir en el intento.

Esta es una simple Aplicación de reflection para obtener un campo:

En el caso de Binding Flags, Especifica los indicadores que controlan el enlace y la forma en que la búsqueda de miembros y tipos que se realiza por reflexión.

Cómo podemos adaptar  Reflection para el entorno Xamarin??

Afortunadamente Microsoft nos provee un Reflection API, que reduce la complejidad al construir automáticamente la jerarquía de elementos basada en la decoración de la clase.

Cuando trabajamos en Xamarin, tradicionalmente entre nuestros proyectos compartidos y el proyecto iOS, es muy probable que tengamos código duplicado. Por eso tenemos disponibles dos APIs genéricas bastante útiles para la aplicación de estos conceptos. Las dos APIs que tenemos disponibles son:

Low-level Elements API: La API de Elementos se basa en la creación de un árbol jerárquico de elementos que representan pantallas y sus componentes.

Hig-level Elements API: También conocida como la API de enlace, en la que las clases se anotan con sugerencias de UI que crea automáticamente pantallas basadas en los objetos y proporciona un enlace entre lo que se muestra (y se edita opcionalmente) en la pantalla, y el respaldo del objeto subyacente.

Supongamos que estamos utilizando una herramienta de análisis estático que se implementa con el nuevo modelo de reflexión. Estamos buscando todos los tipos en una aplicación que se deriven de la clase UIControl. Queremos poder ejecutar esta herramienta en estaciones de trabajo en las que no existe el conjunto UIControl (que contiene la clase UIControl). En este ejemplo, supongamos que abrimos un ensamblaje que contiene una clase que se deriva de la clase UIControl:

Aquí se ve lo que logra la división de referencia / definición. En el nuevo modelo, MyClass es un TypeInfo (definición); sin embargo, BaseType es un Tipo (referencia), y contendrá solo la información sobre UIControl que contiene el ensamblado (MyClass), sin necesidad de encontrar su definición real.

Como vemos simple y rápido, no entraré en muchos detalles, pues mi propósito es que se enamoren del concepto, no se que se abrumen del mismo. Como vemos es un recurso muy útil que puede permitirnos salir de aprietos, como  examinar varios tipos en un dll e instanciar dichos tipos, permite crear nuevos tipos en tiempo de ejecución y realizar alguna tarea usando dichos tipos. En adición a esto, nos peermite identificar si alguna interfaz esta siendo implemetada en alguna clase de nuestra libreria de clases.

Muchas veces queremos obtener ciertas propiedades de determinado control que no se encuentre dentro de Xamarin Forms, y heredamos dicho control e implementamos interfaces,  para lograr el resultado esperado, pero teníamos este concepto claro del todo?

Espero que con este corto(relativamente) articulo puedan entender de forma clara este concepto. Al final,  lo que va a variar es la forma de implementación del mismo según la plataforma, pero no olvidemos la esencia de Reflection.

Aqui les dejo el siguiente recursos para que sigan indagando más sobre el tema:

https://blogs.msdn.microsoft.com/dotnet/2012/08/28/evolving-the-reflection-api/

Hasta la próxima, amigos!