es.davy.ai

Preguntas y respuestas de programación confiables

¿Tienes una pregunta?

Si tienes alguna pregunta, puedes hacerla a continuación o ingresar lo que estás buscando.

Reduciendo ArrayList utilizando los atributos de MyClass

Tengo una clase, MyClass, así:

public class MyClass {
  String name;
  Long amount;
}

public MyClass() {
    // Constructor sin argumentos
}

public Long getAmount() {
    return this.amount;
}

Si quiero obtener la suma de amount en un ArrayList de objetos MyClass, normalmente lo haría así:

// asumiendo ArrayList<myclass> myClassList
Long amount = 0L;
for (MyClass x : myClassList) {
  amount += x.getAmount();
}

Pero ahora, para mejorar el rendimiento, estoy intentando usar Stream.reduce(). Mi enfoque es el siguiente:

// asumiendo ArrayList<myclass> myClassList
// reducir todos los objetos MyClass a un solo objeto MyClass que contenga la cantidad total
Long amount = myClassList.stream().reduce(new MyClass(), 
(curr, next) -> {
  Long currAmount = curr.getAmount() != null ? curr.getAmount() : 0L;  // subtotal
  Long nextAmount = next.getAmount() != null ? next.getAmount() : 0L;  // próximo valor a agregar
  curr.setAmount(currAmount + nextAmount);  // próximo subtotal
  return curr;
}).getAmount();

¿Hay una mejor manera de hacerlo? ¿Y cómo se vería afectada la reducción si currAmount o nextAmount es nulo?

Tags:  ,

Answer

  1. Avatar for davy.ai

    Para mejorar el rendimiento de la obtención de la suma de la cantidad en un ArrayList de elementos MyClass, puedes usar los métodos Stream.mapToLong() y LongStream.sum(), de la siguiente manera:

    // asumiendo ArrayList<myclass> myClassList
    long amount = myClassList.stream().mapToLong(MyClass::getAmount).sum();
    

    Este fragmento de código primero asigna a cada objeto MyClass su propiedad cantidad usando el método mapToLong(), que devuelve un LongStream que contiene todos los valores de cantidad. Luego, llama al método sum() en el LongStream, que devuelve la suma total de todos los valores de cantidad como un primitivo long.

    Esta aproximación es más concisa, clara y potencialmente más eficiente que usar el método reduce() con un acumulador personalizado.

    En cuanto a la reducción que se ve afectada si currAmount o nextAmount es nulo, el código que proporcionaste lo maneja estableciendo el valor nulo en 0L antes de sumarlo al subtotal. Esta es una buena aproximación para evitar posibles NullPointerException. Sin embargo, si deseas manejar los valores nulos de manera diferente, puedes modificar el código dentro de la expresión lambda en consecuencia. Por ejemplo, puedes omitir los valores nulos usando el método filter(), o puedes proporcionar un valor predeterminado usando la clase Optional.

Comments are closed.