A Cozinha da Composição

Boas novas. Acaba de sair o Composite Application Guidance para WPF. Além de exemplos e código fonte que mostram como compor uma interface gráfica, ele contém também uma referência interessante aos patterns utilizados em https://msdn.microsoft.com/en-us/library/cc707841.aspx. Vale uma olhada.

Composição é umas das técnicas mais importantes da computação e tem ganhado novas armas nestas últimas décadas. Começamos com a composição de estruturas de dados e de funções (funções chamando funções) e hoje chegamos à composição de objetos, componentes, classes genéricas, módulos, etc.

Nos 90, meu sonho era instanciar meu site com comandos como new Site<Session<SQLSession>, Security<Https, Token>, ProcessModel<OutProcess>>. Hoje podemos fazer isto de forma elegante e dinâmica usando frameworks para injeção de dependência como o Unity Application Block.

A composição de funções é uma que por vezes é esquecida, mas que vale a pena ser revisitada. Um exemplo: esta semana estava precisando calcular um produto do quadrado dos valores de um array e logo me lembrei do Linq. Não sou expert em Linq e consegui realizar o produto com dois loops invisíveis. Veja o código:

            double [] l = { 1, 2, 3 };

            IEnumerable<double> ld = from o in l select o*o;

            double result = ld.Aggregate<double>((x,y)=>x*y);

Insatisfeito com o duplo loop, parti para implementar uma função que recebe como argumentos o tipo da agregação e a operação para cada elemento do array. Aqui está a função:

public class math

{

    public delegate double f(double x);

    public delegate double oper(double x, double y);

   static public double fromto( IEnumerable<double> l,

oper aggregate_op, f func )

    {

            double result = func(l.First<double>());

            foreach (double d in l.Skip<double>(1))

            {

                result = aggregate_op(result, func(d));

            }

            return result;

  }

}

Veja como ficou simples utilizá-la:

            double [] l = { 1, 2, 3 };

            result = math.fromto(l, (x,y)=>x*y, y=>y*y );

Meu ponto: composição é como o molho de um bom design. Usado com simplicidade e elegância pode dar valor renovado ao seu prato principal.