Home > Enterprise >  How to add particular ids object from list using Java?
How to add particular ids object from list using Java?

Time:12-09

This is my list which is coming in response now I have to add the objects belonging to particular itemIds using Java ,

[
    {
        "data": 210,
        "dataValue":100
        "itemIds": "60e53dee7a814f0001de3538"
    },
    {
        "data": 220,
         "dataValue":120
        "itemIds": "60e53dee7a814f0001de3538"
    },
    {
       "data": 110,
        "dataValue":130
        "itemIds": "60e53dee7a814f0001de3539"
    }
]

Ouput Required ->

[
    {
        "data": 430,
         "dataValue":220
        "itemIds": "60e53dee7a814f0001de3538"
    },
    {
       "data": 110,
        "dataValue":130
        "itemIds": "60e53dee7a814f0001de3539"
    }
]

CodePudding user response:

You could do something like this

import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

public class ListElement {

    public static void main(String[] args) {
        List<ListElement> elements = new ArrayList<ListElement>();
        elements.add(new ListElement(210, 100, "60e53dee7a814f0001de3538"));
        elements.add(new ListElement(220, 120, "60e53dee7a814f0001de3538"));
        elements.add(new ListElement(110, 130, "60e53dee7a814f0001de3539"));

        System.out.println(elements);

        Map<String, List<ListElement>> elementsByItemId = elements.stream() //
                .collect(Collectors.groupingBy(ListElement::getItemId)); //

        elements = elementsByItemId.entrySet().stream() //
                .map(entry -> new ListElement( //
                        entry.getValue().stream().collect(Collectors.summingInt(ListElement::getData)), //
                        entry.getValue().stream().collect(Collectors.summingInt(ListElement::getDataValue)), //
                        entry.getKey())) //
                .collect(Collectors.toList());

        System.out.println(elements);
    }

    int data;
    int dataValue;
    String itemId;

    public ListElement(int data, int dataValue, String itemId) {
        this.data = data;
        this.dataValue = dataValue;
        this.itemId = itemId;
    }

    public int getData() {
        return data;
    }

    public void setData(int data) {
        this.data = data;
    }

    public int getDataValue() {
        return dataValue;
    }

    public void setDataValue(int dataValue) {
        this.dataValue = dataValue;
    }

    public String getItemId() {
        return itemId;
    }

    public void setItemId(String itemId) {
        this.itemId = itemId;
    }

    @Override
    public String toString() {
        return "ListElement [data="   data   ", dataValue="   dataValue   ", itemId="   itemId   "]";
    }

}

CodePudding user response:

Here would be a not perfect example of how to do this. Maybe you can improve this solution to your liking. For simplicity it uses an inner class and exposed fields. I'm sure you will avoid doing this :) It uses a custom aggregating operator and the reduce method of streams (see java stream reduce tutorial or java stream reduce doc)

private static BinaryOperator<Item> itemAggregator = (aggregatedResult, nextElement) -> {
    aggregatedResult.data  = nextElement.data;
    aggregatedResult.dataValue  = nextElement.dataValue;
    return aggregatedResult;
};

public static void something(List<Item> initialItemList) {
    Set<String> uniqueItemIds = initialItemList.stream()
            .map(item -> item.itemId)
            .collect(Collectors.toSet());

    List<Item> resultList = uniqueItemIds.stream()
            .map(itemId -> new Item(0, 0, itemId))
            .collect(Collectors.toList());

    resultList.forEach(
            resultItem -> {
                initialItemList.stream()
                        .filter(item -> item.itemId.equals(resultItem.itemId))
                        .reduce(resultItem, itemAggregator);
    });
}

static class Item {
    public int data;
    public int dataValue;
    public String itemId;

    public Item(int data, int dataValue, String itemId) {
        this.data = data;
        this.dataValue = dataValue;
        this.itemId = itemId;
    }
}

But be aware, that using the reduce method can easily be done wrong (see avoid reduce if possible) and you have to check if it makes sense in your context.

  • Related