quarta-feira, 28 de janeiro de 2009

Interface fluente

Outro pattern interessante é conhecido como carrying return (não confundir com carriage return, carácter com código ASCII 13).
[update 2009-01-29]Esse era o nome dado há uns anos atrás, quando conheci esse pattern. Porém ele não ganhou espaço entre os programadores na época e poucos continuaram usando (como eu). =P

Hoje em dia ele voltou com o nome Fluent Interface, Interface Fluente.

A propósito, troquei o título deste artigo para usar uma linguagem mais nova e mais fácil de ser reconhecida.

Valeu Walter e Lucas![/update]


Há outros nomes, mas não consigo encontrar no São Google, pois não é um pattern muito usado.

Parecido com Smalltalk


Imagine que você tem uma classe Java que recebe muitos parâmetros na instanciação:
Person person = new Person(
aString, aDate, anotherString, aLoad, aPerson, anotherPerson
);


A quantidade de argumentos pode explodir ao extremo. Python pode apresentar maior visibilidade quanto ao significado dos parâmetros:
person = Person(
name=aString,
birthdate=aDate,
id=anotherString,
load=aLoad,
father=aPerson,
mother=anotherPerson
)


Smalltalk, uma linguagem bem mais antiga do que Python ou Java, já tinha uma abordagem bem mais elegante:
person := Person new.
person
setName: aString;
setBirthdate: aDate;
setId: anotherString;
setLoad: aLoad;
setFather: aPerson;
setMother: anotherPerson.


É possível conseguir um código similar em Java usando acessores tipo setter:
Person person = new Person();
person.setName(aString);
person.setBirthdate(aDate);
person.setId(anotherString);
person.setLoad(aLoad);
person.setFather(aPerson);
person.setMother(anotherPerson);


Finalmente


Mas é possível obter um código ainda mais elegante usando o pattern em questão.

A ideia é simples: em vez dos acessores setter não terem retorno (void), basta eles retornarem this:
class Person {
private String name;
private Date birthdate;
private String id;
private Load load;
private Person father;
private Person mother;

public Person() {
name = null;
birthdate = null;
id = null;
load = null;
father = null;
mother = null;
}

public String getName() {
return name;
}

public Person setName(String name) {
this.name = name;
return this;
}

public Date getBirthdate() {
return birthdate;
}

public Person setBirthdate(Date birthdate) {
this.birthdate = birthdate;
return this;
}

public Load getLoad() {
return load;
}

public Person setLoad(Load load) {
this.load = load;
return this;
}

public Person getFather() {
return father;
}

public Person setFather(Person father) {
this.father = father;
return this;
}

public Person getMother() {
return mother;
}

public Person setMother(Person mother) {
this.mother = mother;
return this;
}
}


Agora podemos usar uma estrutura de código similar à de Smalltalk:
Person person = new Person()
.setName(aString)
.setBirthdate(aDate)
.setId(anotherString)
.setLoad(aLoad)
.setFather(aPerson)
.setMother(anotherPerson);


[]'s
Cacilhas, La Batalema
blog comments powered by Disqus