Su principal error es que todavía está pensando en términos más procesales. Esto no pretende ser una crítica de ti como persona, es simplemente una observación. Pensar en términos más funcionales viene con tiempo y práctica, y por lo tanto, los métodos están presentes y se ven como las cosas correctas más obvias para usted. Su error secundario secundario es crear su Opcional dentro de su método. El Opcional está destinado a ayudar a documentar que algo puede o no devolver un valor. Puede que no consigas nada.
Esto te ha llevado a escribir un código perfectamente legible que parece perfectamente razonable, pero te sedujeron las viles tentadoras gemelas que se ponen y están presentes.
Por supuesto, la pregunta se convierte rápidamente en "¿por qué está presente y llega hasta allí?"
Una cosa que mucha gente extraña aquí es que Presente () es que no es algo creado para un nuevo código escrito por personas totalmente conscientes de cuán malditas son las lambdas útiles y a las que les gusta lo funcional.
Sin embargo, nos da algunos (dos) beneficios buenos, geniales y glamorosos (?):
- Facilita la transición del código heredado para usar las nuevas funciones.
- Facilita las curvas de aprendizaje de Opcional.
El primero es bastante simple.
Imagine que tiene una API que se ve así:
public interface SnickersCounter {
/**
* Provides a proper count of how many snickers have been consumed in total.
*/
public SnickersCount howManySnickersHaveBeenEaten();
/**
* returns the last snickers eaten.<br>
* If no snickers have been eaten null is returned for contrived reasons.
*/
public Snickers lastConsumedSnickers();
}
Y tenía una clase heredada usando esto como tal (complete los espacios en blanco):
Snickers lastSnickers = snickersCounter.lastConsumedSnickers();
if(null == lastSnickers) {
throw new NoSuchSnickersException();
}
else {
consumer.giveDiabetes(lastSnickers);
}
Un ejemplo artificial para estar seguro. Pero ten paciencia conmigo aquí.
Java 8 se ha lanzado ahora y estamos luchando por subir a bordo. Entonces, una de las cosas que hacemos es que queremos reemplazar nuestra interfaz anterior con algo que devuelva Opcional. ¿Por qué? Porque como alguien más ya ha mencionado amablemente:
esto elimina las conjeturas de si algo puede ser nulo o no.
Esto ya ha sido señalado por otros. Pero ahora tenemos un problema. Imagine que tenemos (disculpe mientras presiono alt + F7 en un método inocente), 46 lugares donde se llama a este método en código heredado bien probado que de lo contrario hace un excelente trabajo. Ahora tienes que actualizar todo esto.
ESTO es donde brilla IsPresent.
Porque ahora: Snickers lastSnickers = snickersCounter.lastConsumedSnickers (); if (null == lastSnickers) {lanzar una nueva NoSuchSnickersException (); } else {consumer.giveDiabetes (lastSnickers); }
se convierte en:
Optional<Snickers> lastSnickers = snickersCounter.lastConsumedSnickers();
if(!lastSnickers.isPresent()) {
throw new NoSuchSnickersException();
}
else {
consumer.giveDiabetes(lastSnickers.get());
}
Y este es un cambio simple que puede darle al nuevo junior: puede hacer algo útil y podrá explorar la base de código al mismo tiempo. ganar-ganar Después de todo, algo similar a este patrón está bastante extendido. Y ahora no tiene que volver a escribir el código para usar lambdas ni nada. (En este caso particular, sería trivial, pero dejo pensar ejemplos en los que sería difícil como ejercicio para el lector).
Tenga en cuenta que esto significa que la forma en que lo hizo es esencialmente una forma de lidiar con el código heredado sin hacer reescrituras costosas. Entonces, ¿qué pasa con el nuevo código?
Bueno, en su caso, donde solo desea imprimir algo, simplemente haría:
snickersCounter.lastConsumedSnickers (). ifPresent (System.out :: println);
Lo cual es bastante simple y perfectamente claro. El punto que burbujea lentamente hacia la superficie es que existen casos de uso para get () y isPresent (). Están ahí para permitirle modificar mecánicamente el código existente para usar los tipos más nuevos sin pensar demasiado en ello. Por lo tanto, lo que está haciendo está mal orientado de las siguientes maneras:
- Está llamando a un método que puede devolver nulo. La idea correcta sería que el método devuelve nulo.
- Estás utilizando los métodos de bandaid heredados para lidiar con esta opción, en lugar de utilizar los nuevos métodos sabrosos que contienen fantasía de lambda.
Si desea utilizar Opcional como una simple verificación de seguridad nula, lo que debería haber hecho es simplemente esto:
new Optional.ofNullable(employeeServive.getEmployee())
.map(Employee::getId)
.ifPresent(System.out::println);
Por supuesto, la buena versión de esto se ve así:
employeeService.getEmployee()
.map(Employee::getId)
.ifPresent(System.out::println);
Por cierto, aunque de ninguna manera es obligatorio, recomiendo usar una nueva línea por operación, para que sea más fácil de leer. Fácil de leer y comprender mejor que la concisión cualquier día de la semana.
Por supuesto, este es un ejemplo muy simple en el que es fácil entender todo lo que estamos tratando de hacer. No siempre es así de simple en la vida real. Pero observe cómo en este ejemplo, lo que estamos expresando son nuestras intenciones. Queremos OBTENER el empleado, OBTENER su identificación y, si es posible, imprimirlo. Esta es la segunda gran victoria con Opcional. Nos permite crear un código más claro. También creo que hacer cosas como hacer un método que haga un montón de cosas para que puedas alimentarlo a un mapa es, en general, una buena idea.