En realidad, puede ampliar Consumer
(y Function
etc.) con una nueva interfaz que maneja excepciones, ¡utilizando los métodos predeterminados de Java 8 !
Considere esta interfaz (se extiende Consumer
):
@FunctionalInterface
public interface ThrowingConsumer<T> extends Consumer<T> {
@Override
default void accept(final T elem) {
try {
acceptThrows(elem);
} catch (final Exception e) {
// Implement your own exception handling logic here..
// For example:
System.out.println("handling an exception...");
// Or ...
throw new RuntimeException(e);
}
}
void acceptThrows(T elem) throws Exception;
}
Entonces, por ejemplo, si tiene una lista:
final List<String> list = Arrays.asList("A", "B", "C");
Si desea consumirlo (por ejemplo, con forEach
) con algún código que arroje excepciones, tradicionalmente habría configurado un bloque try / catch:
final Consumer<String> consumer = aps -> {
try {
// maybe some other code here...
throw new Exception("asdas");
} catch (final Exception ex) {
System.out.println("handling an exception...");
}
};
list.forEach(consumer);
Pero con esta nueva interfaz, puede crear una instancia con una expresión lambda y el compilador no se quejará:
final ThrowingConsumer<String> throwingConsumer = aps -> {
// maybe some other code here...
throw new Exception("asdas");
};
list.forEach(throwingConsumer);
¡O incluso solo para que sea más sucinto !:
list.forEach((ThrowingConsumer<String>) aps -> {
// maybe some other code here...
throw new Exception("asda");
});
Actualización : Parece que hay una muy buena parte de la biblioteca de servicios de Durian llamada Errores que se puede usar para resolver este problema con mucha más flexibilidad. Por ejemplo, en mi implementación anterior, he definido explícitamente la política de manejo de errores ( System.out...
o throw RuntimeException
), mientras que los Errores de Durian le permiten aplicar una política sobre la marcha a través de un amplio conjunto de métodos de utilidad. Gracias por compartirlo , @NedTwigg !.
Uso de la muestra:
list.forEach(Errors.rethrow().wrap(c -> somethingThatThrows(c)));