Archive for December 23, 2009

Haskell, C# y Currying

Aunque el concepto de “Currying” no es algo extraño para los lenguajes funcionales (y por lo tanto bastante conocido entre usuarios de este tipo de lenguajes). No es sólo una palabra extraña sino un concepto quizás desconocido para muchos usuarios de lenguajes imperativos como C#.

Currying (llamado así en nombre de Haskell Curry) no es más que el efecto de tomar de forma individual parámetro por parámetro y procesar cada parámetro por separado en su propia función, esto lo logramos tranformando el método o función en cuestión por uno que tome uno de los parámetros y una función para luego retornar otra función. Por ejemplo, tomemos el hecho de una simple suma:

sum       :: (Int, Int) -> Int
sum (x, y) = x + y

En este caso indicamos una función llamada sum que toma dos parámetros de tipo Int y retorna un parámetro de tipo Int. Dado que las funciones son ciudadanos de primer orden en los lenguajes funcionales, podemos transformarla y definir una función que tome como uno de sus parámetros una función y retorne otra función

sum'     :: Int -> Int -> Int
sum' x y = x + y

En este caso, creamos la función sum’ que toma un parámetro tipo Int y retorna otra función que toma un parámetro tipo Int y retorna un Int. Si, ya se que a simple vista esto puede parecer extraño, pero regresemos a ver un par de puntos claves: Currying involucra evaluar uno a uno los parámetros de una función pudiendo retornar otra función en su lugar.

Bien, regresemos a la Tierra y veamos como podemos transformar este tipo de cosas en una forma más "C#". Aprovechando los métodos lambda en C# (otra adición netamente funcional) podemos describir algo como esto:

public static void Main()
{
    Func<int, int, int> sum =
        (x, y) => x + y;

    int result = sum(1,2);

    Console.WriteLine(result);
}

Pero que les parecería si cambiamos "un poco" la definición de la función sum:

public static void Main()
{
    Func<int, Func<int, int>> sum =
        x => y => x + y;

    int result = sum(1)(2);
    Console.WriteLine(result);
}

Ahora sum en vez de tomar dos enteros como parámetro y retornar un entero, ahora toma un entero retorna una función (que toma un entero y retorna otro entero) como parámetros. De esta manera sum(1) retornará otra función que luego toma el parámetro 2 y retorna 3, wow…

El concepto de currying es práctico, permite definir funciones complejas a partir de funciones mucho más simples, aunque la definición en C# parece compleja, en realidad permite definir una función a partir de simplemente un parámetro (el cual convenientemente puede permanecer dentro de la función como si fuera una constante).

public static void Main()
{
    Func<int, Func<int, int>> ntimes =
        x => y => x * y;

    var twice = ntimes(2);
    var three = ntimes(3);

    Console.WriteLine(twice(4));
    Console.WriteLine(three(4));
}

Es interesante todo lo que podríamos lograr con solamente un poco de imaginación. :)

C# y el caracter Wildcard de Haskell

Escuchando al Dr. Meijer en su serie Functional Programming with Haskell, me topé con algo interesante: el caracter wildcard de Haskell. El "wildcard” (_) en Haskell es prácticamente lo mismo que el caracter wildcard (*) en nuestros sistemas operativos, evalúa o implica cualquier “otra cosa”. Por ejemplo:

(&&)         :: Bool -> Bool -> Bool
True && True = True
_ && _       = False

Tiene una interpretación sumamente sencilla: “Dada una función llamada &&, que toma un Bool y retorna una función que toma un Bool y retorna un Bool siendo sus parámetros True y True retornará True, de cualquier otra manera, retornará False”. A simple vista pensaremos que en lenguajes de “diario” no existen conceptos como el de “wildcard”, pero como lo dice luego el Dr. Meijer, en C# si tenemos el concepto de wildcard, claro, con nuestros amigos los Generics (otro concepto tomado de lenguajes funcionales y que data de muchos años atrás :P ).

En C# el guión bajo es un nombre aceptado de una variable, así que podemos utilizarlo como caracter de wildcard (a lo Haskell), imaginemos la declaración desiguiente tipo genérico:

public interface IRepository<T> {
    T GetById(int id);
}

Bien, que tal si lo nombramos algo así:

public interface IRepository<_> {
    _ GetById(int id);
}

Debo admitir que en mi caso lo veo algo extraño para los tipos de retorno… Que tal si usamos un wildcard para aquellos tipos que "debemos" definir pero que no "vamos" a utilizar.

// Siendo esta la declaración de un evento
runtime.RuntimeStarted += (sender, e) => Console.WriteLine(e.InstanceId);

// De igual manera, sender es un Object el cual no utilizamos
runtime.RuntimeStarted += (_, e) => Console.WriteLine(e.InstanceId);

Si, ya se que más de algún usuario de VB.NET me comentará que en VB9 no es necesario declarar en los eventos aquellos parámetros que no utilizaremos, pero esa es harina de otro costal.

Al parecer si hay un par de cosas que un usuario de C# puede aprender de Haskell… Saludos!

Haskell y los lenguajes funcionales

programming haskell Soy fiel creyente que todo _buen_ desarrollador debe aprender por lo menos dos lenguajes nuevos por año, algunas otras personas diferiran conmigo y esgrimiran el dicho “es que hay que ser bueno y realmente bueno en una sola cosa”, y no estoy para discutir eso (para dejarlo claro, no creo que deba ser así, pero ese es otro tema).

Creo firmemente que aprender un lenguaje NO se trata de aprender sus palabras claves, ni sus librerias (aunque ciertamente podemos aprender mucho de ellas) o incluso, creer que porque hacemos el “hola mundo” ya conocemos de que se trata, gran error a mi parecer. Aprender un lenguaje lleva consigo aprender su “razón de ser”, enteder el problema que resuelve, comprender el porqué fue hecho, y si es posible, acoplar o absorver las buenas cosas que su paradigma comprende en nuestro lenguaje “de diario” que puedan ayudarnos y hacernos mejores desarrolladores.

En estas últimas semanas me decidí a tratar de comprender un poco acerca de lenguajes funcionales (algunos habran escuchado F#, ese es un ejemplo de un lenguaje funcional en la .Net Framework, Scala es otro en la Java VM) y como lenguaje modelo decidí aprender con Haskell, un lenguaje diseñado para la enseñanza de lenguajes funcionales, de esta manera aprovechaba una excelente colección de videos acerca de Functional Programming with Haskell a cargo del Dr. Erik Meijer (un señor sumamente inteligente y chistoso si me preguntan) los cuales estan disponibles para bajar del sitio de Channel 9, junto con las diapositivas y ejercicios de ejemplo, claro, deben acompañar la lecture con el libro de Programming in Haskell de Graham Hutton (de hecho las lecciones del Dr. Meijer estan basadas en el libro y estan diseñadas para darle seguimiento a cada uno de los capítulos del libro. Concejo, consigan el libro).

Me parece sumamente interesante el comienzo del libro y de las lecciones del Dr. Meijer. Soy fanático de la historia y comenzar una lecture con “historia de los lenguajes funcionales” me pareció impresionante, quizás exagero, pero creo que si los cursos universitarios incluyeran un “historia del arte de las ciencias de la computación” crearíamos profesionales un poco más concientes de que rayos se trata el oficio de computer sciences (o computer engineering, como prefieran), bueno, quizás ya estoy divagando un poco… Es increíble cosas que damos como “recientes” o “nuevas” realmente fueron ideadas por mentes sumamente billantes hace ya muchos años. Cosas como los Domain Specific Languages (DSL) y características ya más que conocidas como type inference y lazy evaluation datan desde los años 70. Quizás si vemos la historia nos daremos cuenta de qué es lo siguiente a venir en los próximos años.

Ahí les contaré que tal me va con Haskell. Hasta el próximo post!

SyntaxHighlighter 2.0 Haskell Brush

I know there are a lot of Syntax Highlighter out there, but I love Alex Gorbatchev SyntaxHighlighter 2.0.

I had to write a new brush for Haskell language since I start searching for one without any success, this is my first attempt to make a SyntaxHighlighter Brush (and I just starting learning haskell a few weeks ago).

module sample where
{-
Multiline comments
this is a comment too
-}
isDigit :: Int -> Int
abs | n >= 0 = n
    | otherwise = -n
-- Single line comments allowed

You can get the simple brush here http://gist.github.com/261919

Calculando la fecha UTC en SQL Server

Hace unos días me topé con algo interesante, cambiar la fecha ya establecida en los campos de una tabla a una estandarizada para varios paises. La solución simple fue utilizar la fecha UTC (GMT 0), pero ya en SQL Server las fechas estaban registradas con la hora local.

En SQL Server podemos obtener el tiempo actual UTC con la función GETUTCDATE(), utilizando esto a nuestro favor decidí crear un simple UDF para cambiar las fechas.

CREATE FUNCTION [dbo].[ConvertToUtc](@start datetime)
RETURNS DATETIME
AS
BEGIN
    DECLARE @offset INTEGER
    SET @offset = DATEDIFF(HOUR, GETUTCDATE(), GETDATE())
    RETURN DATEADD(HOUR, @offset, @start)
END

Luego el proceso es simple, como ejemplo, transformando la fecha actual a UTC:

SELECT ConvertToUtc(CURRENT_TIMESTAMP)