Andrew
Andrew

Reputation: 4712

Kotlin: How to check if a mutabeListOf<Pair<Object, Int>> already contains a specific Object?

I want to check if a mutableListOf<Pair<Product, Int>> already contains a product with a specific name. If there is a Pair<Product, Int> with the searched name, the Int value of this product should be increased.

Here is my approach:

fun main() {
    val item = Item()
    
    val prod1 = Product("Test")
    val prod2 = Product("Test")

    item.addProduct(prod1, 1)
    item.addProduct(prod2, 5)

   for ((prod,amount) in item) println("$Productname: {prod.productName}, $amount")
}

The Output should be:

Productname: Test, 6

and not:

Productname: Test, 1

Productname: Test, 5

Here the Product Class:

class Product(val productName: String) {
    // other stuff that is unnecessary for the question
}

And the Item Class:

class Item {
    private val pairList = mutableListOf<Pair<Product, Int>>()

    fun addProduct(product: Product, quantity: Int) {
        for (prod in pairList) {
            if (pairList.contains(Pair(product, quantity))){
                val value = prod.second + quantity
                prod.copy(second = value)
            } else {
                pairList.add(Pair(product, quantity))
            }
        }
    }
}

Currently, nothing works (neither the comparison nor adding a new Pair). I appreciate every post!

Upvotes: 0

Views: 2030

Answers (1)

Giorgio Antonioli
Giorgio Antonioli

Reputation: 16214

Here there are two possibilities depending on your needs.

1. Use MutableMap<Product, Int>

This is a perfect use-case to use a MutableMap<K, V> instead of MutableList<Pair<K, V>> since you need to find the current quantity for a given product and increase it:

private val productMap = mutableMapOf<Product, Int>()

fun addProduct(product: Product, quantity: Int) {
    val foundQuantity = productMap[product]
    // Increase the found quantity by [quantity] or add the given [quantity].
    val finalQuantity = foundQuantity?.let { it + quantity } ?: quantity
    productMap[product] = finalQuantity
}

To do this, you should make your Product class a data class (or implement manually equals and hashcode) to be able to compare the hash of two Products using their productName value.

data class Product(val productName: String) { ... }

The pros of this solution are the fast lookups and the fast insertions. The cons of this solution is that your products won't be sorted anymore.

2. Use MutableList<Pair<Product, Int>>

If you need your products sorted and you need to maintain the same insertion order, you can still use a list making some optimizations.

private val pairList = mutableListOf<Pair<Product, Int>>()

fun addProduct(product: Product, quantity: Int) {
    pairList.forEachIndexed { index, (savedProduct, savedQuantity) ->
        if (savedProduct.productName == product.productName) {
            // This is the product we are searching for.
            pairList[index] = product to quantity + savedQuantity
            // We found the product and replaced it, we don't need to search for it anymore.
            return
        }
    }
    // We didn't find a product, add it as the last item.
    pairList += product to quantity
}

Upvotes: 2

Related Questions