Tengo el siguiente código que es un poco feo para múltiples comprobaciones nulas.
String s = null;
if (str1 != null) {
s = str1;
} else if (str2 != null) {
s = str2;
} else if (str3 != null) {
s = str3;
} else {
s = str4;
}
Así que intenté usar Optional.ofNullable
como se muestra a continuación, pero aún es difícil de entender si alguien lee mi código. cuál es el mejor enfoque para hacerlo en Java 8.
String s = Optional.ofNullable(str1)
.orElse(Optional.ofNullable(str2)
.orElse(Optional.ofNullable(str3)
.orElse(str4)));
En Java 9, podemos usar Optional.ofNullable
con OR
, pero en Java8, ¿hay algún otro enfoque?
or
sintaxis de Java9String s = Optional.ofNullable(str1) .or(() -> Optional.ofNullable(str2)) .or(() -> Optional.ofNullable(str3)) .orElse(str4);
no se ve tan bien como la queStream.of
yo haría.StringUtils.firstNonBlank()
Respuestas:
Puedes hacerlo así:
fuente
{str1, str2, str3}
) parece mucho más lento que un localif
o?:
, que el tiempo de ejecución de Java puede optimizar. ¿Hay alguna optimización específica de Streamjavac
y el tiempo de ejecución de Java que lo hace tan rápido como?:
? De lo contrario, no recomendaré esta solución en código de rendimiento crítico.?:
código y estoy seguro de que debería evitarlo en el código de rendimiento crítico. Sin embargo, es mucho más legible y debería recomendarlo en un código que no es crítico para el rendimiento, en mi opinión, que estoy seguro de que genera más del 99% del código.javac
ni en el tiempo de ejecución. Esto no excluye las optimizaciones generales, como incluir todo el código, seguido de la eliminación de operaciones redundantes. En principio, el resultado final podría ser tan eficiente como las expresiones condicionales simples, sin embargo, es bastante poco probable que llegue allí, ya que el tiempo de ejecución gastaría el esfuerzo necesario solo en las rutas de código más calientes.str4
a los parámetros deStream.of(...)
y usarorElse(null)
al final.¿Qué hay del operador condicional ternario?
fuente
// take first non-null of str1..3
. Una vez que sepa lo que hace, es fácil ver cómo.?:
escalera, sabrá lo que hace. (Por cierto, los programadores funcionales saben esto como(cond ...)
cláusulas:. Siempre es un guardia seguido por el valor apropiado utilizar cuando el guardia es verdad)También puede utilizar un bucle:
fuente
Las respuestas actuales son buenas, pero realmente deberías ponerlas en un método de utilidad:
Ese método ha estado en mi
Util
clase durante años, hace que el código sea mucho más limpio:Incluso puedes hacerlo genérico:
fuente
Arrays.stream()
cuando puedo hacer lo mismo con ayfor
a!= null
, que es más eficiente. Y Todd tendría razón. Sin embargo, cuando codifiqué este método, estaba buscando una forma de hacerlo usando las funciones de Java 8, al igual que OP, así que ahí está.Yo uso una función auxiliar, algo así como
Entonces este tipo de código se puede escribir como
fuente
v0
parámetro extra ?min
como ejemplo). Estoy menos convencido de que esto sea apropiado aquí.firstNonNull(arr)
devolver arr si no es nulo. Si lo fuerafirstNonNull(T... vs)
, devolvería la primera entrada no nula en arr.Una solución que se puede aplicar a tantos elementos como desee puede ser:
Podrías imaginar una solución como la siguiente, pero la primera asegura
non nullity
todos los elementos.fuente
str4
pesar de que sea un nulo en realidadorElseNull
, que equivale a lo mismo sistr4
es nulo.También puede agrupar todas las cadenas en una matriz de cadenas y luego hacer un bucle for para verificar y romper el bucle una vez que esté asignado. Suponiendo que s1, s2, s3, s4 son todas cadenas.
Editado para poner en condición por defecto a s4 si no se asigna ninguno.
fuente
s4
(ostr4
), que se supone que se asignará als
final, incluso si es nulo.Método sencillo y basado en el método.
Y utilícelo como:
Es fácil de hacer con matrices y se ve bonito.
fuente
Si usa Apache Commons Lang 3, entonces se puede escribir así:
Se
ObjectUtils.firstNonNull(T...)
tomó el uso de esta respuesta . También se presentaron diferentes enfoques en una pregunta relacionada .fuente