O método forEach na interface Iterable
- Antes do Java 8: O método forEach não existia. 
- Problema ao adicioná-lo diretamente em List: Todas as classes que implementam List teriam que redefini-lo e bibliotecas como Hibernate poderiam quebrar, gerando NoSuchMethodError. 
Default Methods
- O Java 8 introduziu métodos default em interfaces, permitindo que métodos tenham implementação dentro da própria interface. 
- O método forEach foi adicionado na interface Iterable, que é mãe de Collection e, consequentemente, de List. 
default void forEach(Consumer<? super T> action) {
    Objects.requireNonNull(action);
    for (T t : this) {
        action.accept(t);
    }
}
- Como ArrayList implementa List, ele automaticamente herda forEach. 
- O método recebe um objeto da interface funcional Consumer, que tem o método accept(T t). 
- Exemplo de uso com lambda: 
usuarios.forEach(u -> System.out.println(u.getNome()));
A interface Consumer não tem só um método!
- Uma interface funcional possui apenas um método abstrato. 
- Pode conter métodos default, desde que tenha apenas um método abstrato. 
- A anotação @FunctionalInterface pode ser usada para indicar que uma interface segue essa regra. 
A Interface Consumer
- O Consumer é uma interface funcional do pacote java.util.function. 
- Possui o método abstrato: - void accept(T t);
- Também tem um método default chamado andThen que permite compor múltiplos consumidores, executando-os em sequência: 
default Consumer<T> andThen(Consumer<? super T> after) {
    Objects.requireNonNull(after);
    return (T t) -> { accept(t); after.accept(t); };
}
Exemplo de Uso do andThen
- Criamos dois Consumer: Um exibe uma mensagem antes da impressão. Outro imprime o nome do usuário. 
- O andThen permite que ambos sejam aplicados na lista de usuários. 
Consumer<Usuario> mostraMensagem = u -> 
    System.out.println("antes de imprimir os nomes");
Consumer<Usuario> imprimeNome = u -> 
    System.out.println(u.getNome());
usuarios.forEach(mostraMensagem.andThen(imprimeNome));
Reutilização e o Padrão Decorator
- Podemos criar implementações reutilizáveis de Consumer. 
- Exemplo: um Consumer auditor que registra logs pode ser usado isoladamente ou combinado com andThen. 
- Essa abordagem se assemelha ao Padrão Decorator, permitindo a composição dinâmica de comportamentos. 
Obs.:
O Padrão Decorator é um padrão de projeto estrutural que permite adicionar funcionalidades a um objeto dinamicamente, sem modificar sua estrutura original. Ele encapsula um objeto dentro de outro para estender ou modificar seu comportamento. No exemplo com Consumer, usamos o método andThen para compor múltiplos comportamentos. Isso é semelhante ao Decorator, pois adicionamos novas ações sem modificar o Consumer original.
 

 
    
Top comments (0)