Saltar al contenido

Kotlin: Suma de BigDecimal en una lista

Solución:

Justo como lo has usado Collectors.reducing en java, puedes usar fold o reduce funciones de extensión en Kotlin:

val bigDecimals: List<BigDecimal> = ...
val sum = bigDecimals.fold(BigDecimal.ZERO) { acc, e -> acc + e }
// or
val sum2 = bigDecimals.fold(BigDecimal.ZERO, BigDecimal::add)

El ejemplo completo en play.kotlinlang.org: https://pl.kotl.in/o6pRhrqys

Empezando con Kotlin 1.4 ahora hay una función sumOf, que toma una función de selector y suma todos los valores devueltos por este selector, por lo que puede usarlo de la siguiente manera:

val totalById = list
                .groupBy { it.id }
                .mapValues { it.value.sumOf { it.amount } }

El ejemplo completo en play.kotlinlang.org: https://pl.kotl.in/jXAfoyff-

Puedes crear el tuyo propio sumByBigDecimal función de extensión similar a sumByDouble. p.ej:

/**
 * Returns the sum of all values produced by [selector] function applied to each element in
 * the collection.
 */
inline fun <T> Iterable<T>.sumByBigDecimal(selector: (T) -> BigDecimal): BigDecimal {
    var sum: BigDecimal = BigDecimal.ZERO
    for (element in this) {
        sum += selector(element)
    }
    return sum
}

Uso de ejemplo:

val totalById = list
        .filter { it.status == StatusEnum.Active }
        .groupBy { it.item.id }
        .mapValues { it.value.sumByBigDecimal { it.amount } }

Combinando el enfoque de plegado y el enfoque de función de extensión, puede hacer esto:

fun Iterable<BigDecimal>.sumByBigDecimal(): BigDecimal {
    return this.fold(BigDecimal.ZERO) { acc, e -> acc + e }
}

fun <T> Iterable<T>.sumByBigDecimal(transform: (T) -> BigDecimal): BigDecimal {
    return this.fold(BigDecimal.ZERO) { acc, e -> acc + transform.invoke(e) }
}

Úselos así:

listOfBigs.sumByBigDecimal()

listOfWidgets.sumByBigDecimal { it.price }
¡Haz clic para puntuar esta entrada!
(Votos: 0 Promedio: 0)


Tags :

Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *