Diseño

Sistema de plugins con C#. Parte II. El código explicado

Antes de empezar

Como indiqué en la parte final del artículo anterior este artículo se ha retrasado tanto que he decidido sacar el código antes de estar acabado. Pese a que la parte fundamental del código es correcta, sobre todo a los efectos de ilustrar este artículo, no debe considerarse en producción y no recomiendo utilizarla para su uso en ninguna aplicación "real", al menos hasta que publique la versión completa.

La web del proyecto y su licencia

El código y otra información adicional está disponible en la página del proyecto Monet Plugins Library y tenéis disponible la última versión del código en el control de versiones de subversion http://svn.thealphasite.org/Monet.

Todo el proyecto responde a la licencia LGPL, lo cual implica, a grandes rasgos que el proyecto es esencialmente GPL (con todas las obligaciones que ello conlleva, como distribuir las modificaciones echas al código y mantener la misma licencia) pero permitiendo que el framework sea utilizado dese una aplicación o librería que no sea GPL. En general esta es una de las licencias que más "libre" me parece. Básicamente, si quieres modificarla y mejorarla tienes que "devolver" lo que has hecho y por tanto la librería va mejorando constantemente, pero si simplemente quieres usarla desde algún otro programa, entonces no encuentras restricciones.

Test Driven Development (Desarrollo dirigido por las pruebas)

Ultimamente, aquí y allá estoy oyendo hablar del llamado Test Driven Development o Desarrollo guiado por las pruebas como nueva metodología de desarrollo.

Dejadme que os explique un poco como funciona el asunto. La metodología se basa en que el desarrollo de los test guie el desarrollo de la aplicación, de esta forma lo primero que hacemos es planear que necesita hacer la aplicación y en función de ello desarrollamos test para cada una de las funciones, de esta forma disponemos de una prueba para cada función (no os entusiasmeis demasiado con esto ...)

El siguiente paso evidentemente es desarrollar la funcionalidad que consigue pasar ese test, y por tanto, funcionalidad hecha y medianamente probada... perfecto.

La descripción de la metodología tiene más pasos y más guías para el desarrollo y como realizar cada paso. La página de la wikipedia tiene más información para los interesados (que espero que después de leer este artículo sean pocos).

El misterio del bloque try vacio

El misterio

Hace bien poco he leido un interesante artículo (en inglés) llamado "The empty try block mystery" que describe algunas secciones de código presentes en el código fuente del .NET Framework y que son similares a lo siguiente:

try
{
}
finally
{
  HazCosas1();
  HazCosas2();
}

y que responde a la pregunta ¿porque diablos iba alguien a declarar un bloque try finally estando el try vacío? Pues vamos a explicarlo, en español ;)

Sistema de plugins con C#. Parte I. Conceptos

Antes de empezar

Un sistema de plugins es un mecanismo complejo. Por un lado el traslado de dependencias hacia el tiempo de ejecución (como veremos más adelante) lo hace mucho más complicado de explicar, de comprender y de implementar. Hay muchas cuestiones a tener en cuenta, este artículo trata de abarcar las principales pero me temo que hay muchas cuestiones que quedarán fuera.

Por otro lado, aunque para entender el sistema no es necesario un conocimiento de .NET o C#, desde luego estos puntos ayudarán a comprenderlo mejor y con más profundidad.

Evidentemente el sistema es demasiado complejo para que explique aquí todas y cada una de las partes que componen el sistema. El código en si, que incluyo en el artículo, está bastante comentado y he procurado ilustrar en el artículo las partes principales del sistema pero no me cabe duda de que habrá zonas que queden sin comentar.

Por último, este es un artículo largo y complejo y aunque he intentado en la medida de lo posible que tanto el código como el artículo esten libre de errores puede que alguno se haya colado, si encontrais alguno o teneis algún comentario os ruego que me lo hagais saber, bien por comentarios o bien directamente contactando conmigo en el email de contacto.

Introducción a Bases de Datos

Introducción

En estos tiempos, con las modernas aplicaciones informáticas que existen hoy en día, los programadores en ocasiones olvidamos que tanto los propios ordenadores como los programas que ejecutan sobre ellos no son más que procesadores de datos, procesadores rápidos, pero procesadores a fin de cuentas.

Los programas en realidad recojen datos del usuario, de archivos en el ordenador, de la entrada de los periféricos y los transforman para producir otros datos. Una aplicación como el photoshop por ejemplo recoje los datos almacenados en forma de bytes en un fichero y permite al usuario mediante la introducción de toda una serie de datos modificarlos para crear otra imagen distinta. La tarjeta gráfica transforma una serie de datos en forma de stream de bytes en secuencias de 24 bits que a su vez el monitor transforma en pixels en la pantalla.

Todo en informática está basado en los datos. Mucha gente, cuando oye hablar de base de datos automáticamente piensa en Microsoft Access o en Oracle o en cualquiera de los motores de bases de datos disponibles en el mercado. En realidad una base de datos es, como su nombre indica, cualquier almacen de datos, ni siquiera es en realidad necesario que dicho almacen sea informático, el termino podría valer para cualquier almacen de datos, como por ejemplo una biblioteca. Las bases de datos actuales, con su organización y sus características propias (SQL, indices, etc) responden a una necesidad creciente de acceder a los datos de la forma más rápida y estructurada posible.

Comentado de código y documentación.

Table of Contents [hide]

Comentando código

Realizar comentarios en el código es algo fundamental para la mantenibilidad de este cuando lo volvamos a coger más adelante.

Muchas veces, sobre todo en los proyectos esos que son "para anteayer" las prisas y la necesidad de tener la versión o el producto listo para una determinada fecha hacen que los comentarios de código sean escasos, malos o inexistentes.

Al contrario de lo que puedan decir por ahí no voy a decir, "comenta siempre aunque tengas que retrasarte"; nada más lejos de la realidad, acaba el proyecto, entregalo y consigue el dine

Tipos de datos. Tabla Hash

Introducción

Una tabla hash es una estructura de datos que permite asociar claves con valores y cuya principal ventaja es una complejidad de inserción y busqueda de O(1) (O(n) en el peor de los casos).

Cuando tenemos la necesidad de almacenar datos en memoria tenemos una serie de opciones (listas enlazadas, arrays, arboles...) cada una de las cuales tienes sus ventajas y sus inconvenientes que normalmente consisten en establecer un compromiso entre espacio en memoria y velocidad.

Una lista enlazada aprovecha completamente el espacio de memoria pero la velocidad de busqueda es lineal, para encontrar un elemento debemos ir recorriendo la lista hasta encontrarlo, en un array reservamos toda la memoria que podríamos por adelantado pero por contra obtenemos un rendimiento de busqueda constante O(1). Los arboles constituyen una variación de las listas enlazadas en las cuales se mejora el rendimiento de busqueda (O(log(n))) a cambio de empeorar el rendimiento de inserción.

Las tablas hash constituyen una forma de obtener un rendimiento (casi) constante controlando la cantidad de memoria que deseamos compromenter, cuanto más pequeña sea la tabla mayor será el impacto sobre el rendimiento de la tabla debido al numero de colisiones.

Singletons en Delphi

Cuando programas en delphi y has programado en un lenguaje como C++ o C# que permiten clases estáticas llegas a echarlas un poco de menos puesto que son un recurso muy util.

¿Qué es una clase estática?

Una clase estática es, simplificando, una clase que proporciona una serie de metodos pero que no necesita ser instanciada, es decir, no necesitas crear un objeto de la clase para poder llamar a sus metodos.

En realidad en c# está separación llega al nivel de metodo, es decir, es posible definir determinados metodos de una clase como estáticos y otros no, de forma que se pueda llamar a dichos metodos sin necesidad de instanciar la clase, más o menos en C# viene a ser algo así:

public class MiClaseEstatica
{
  private int m_value;

  public MiClaseEstatica()
  {
    m_value = 0;
  }


  public int Value(){ return m_value; }

  public static int RestoDeDivisionConBucle(int numerador, int denominador)
  {
    int resultado = numerador;
    while (resultado < denominador)
    {
      resultado = resultado - denominador;
    }

    return resultado;
  }
}

De está forma la clase tiene dos funciones una de las cuales es estática y otra no, de forma que podemos hacer una invocación como:

MiClaseEstatica.RestoDeDivisionConBucle(30,4);

pero no podríamos invocar la función Value sin crear una instancia de la clase.

Tipos de Datos. Pipe (Tubería)

Introducción

Un pipe o tubería es una estructura de datos que representa un canal de comunicación con una estructura de tipo FIFO (primero en entrar, primero en salir).

La denominación de tubería (en ingles pipe) viene del concepto de que los datos que introducimos o empujamos por un extremo de la tubería "aparecen" en el extremo contrario. Si realizamos una operación de lectura en la tubería y no hay datos en esta el hilo llamante se quedará bloqueado hasta que haya datos. Si realizamos una escritura en la tubería y esta ha alcanzado su tamaño máximo el proceso que desea escribir en la tubería se quedará bloqueado hasta que algun lector saque un dato.

Reference couting (conteo referencial).

Introducción.

¿Qué es reference counting?

Reference counting es una técnica que se utiliza cuando necesitas mantener varias referencias a un mismo sitio, o más concretamente a un mismo objeto sin tener que tener varias copias de dicho objeto en memoria.

El problema derivado de hacer referencia a un objeto desde varios sitios consiste en la liberación del objeto, es decir, en el momento de liberar la memoria del objeto. Dicha liberación no constituye un problema en lenguajes con un buen recolector de basura (como C#) pero puede suponer una enorme fuente de memory leaks en otros proyectos. Por ejemplo, supongamos que tenemos algo como esto (el código es en c++ pero vale igual en delphi)