将两个数组列表中的值相加,然后返回第三个列表

时间:2019-09-12 04:51:46

标签: java

通过汇总与两个列表中相同元素相关的数据来创建第三个数组列表,否则插入新数据

我用Id作为键从两个数组列表中创建了两个映射,然后通过组合两个映射中的键来创建一个集合。利用集合中的值,我查询了两个列表并得出了总和。如果遵循这种方法,我会看到预期的输出,但是想知道在Java 1.6中是否还有其他有效的方法可以实现这一目标

---------------- Java ----------------

public class Stock {

    private int stockCode;
    private int stockQuantity;
    private int stockValue;

    public int getStockCode() {
        return stockCode;
    }

    public int getStockQuantity() {
        return stockQuantity;
    }

    public int getStockValue() {
        return stockValue;
    }

    public Stock(int stockCode, int stockQuantity, int stockValue) {
        this.stockCode = stockCode;
        this.stockQuantity = stockQuantity;
        this.stockValue = stockValue;
    }

    public static void main(String[] args){
        List<Stock> oldStock = new ArrayList<Stock>();
        Stock s1 = new Stock(1,  20, 16000);
        Stock s2 = new Stock(2, 10, 5000);
        Stock s3 = new Stock(3,  15, 3000);
        oldStock.add(s1);
        oldStock.add(s2);
        oldStock.add(s3);

        List<Stock> newStock = new ArrayList<Stock>();
        Stock s4 = new Stock(5, 5, 2500);
        Stock s5 = new Stock(1, 10, 8000);
        Stock s6 = new Stock(3, 10, 2000);
        newStock.add(s4);
        newStock.add(s5);
        newStock.add(s6);

        List<Stock> netStock = new ArrayList<Stock>();

        Map<Integer, Stock> oldStockMap = new HashMap<Integer, Stock>();
        for(Stock os:oldStock){
            oldStockMap.put(os.getStockCode(),os);
        }
        Map<Integer, Stock> newStockMap = new HashMap<Integer, Stock>();
        for(Stock ns:newStock){
            newStockMap.put(ns.getStockCode(),ns);
        }
        Set<Integer> keySet = new HashSet<Integer>();
        keySet.addAll(oldStockMap.keySet());
        keySet.addAll(newStockMap.keySet());

        for(Integer ks:keySet){
            Integer netStockQ=0;
            Integer netStockV=0;
            if(oldStockMap.get(ks)!=null && newStockMap.get(ks)!=null) {
                netStockQ =oldStockMap.get(ks).getStockQuantity() + newStockMap.get(ks).getStockQuantity();
                netStockV = oldStockMap.get(ks).getStockValue() + newStockMap.get(ks).getStockValue();
            } else if(oldStockMap.get(ks)==null && newStockMap.get(ks)!=null){
                netStockQ = newStockMap.get(ks).getStockQuantity();
                netStockV = newStockMap.get(ks).getStockValue();
            } else if(oldStockMap.get(ks)!=null && newStockMap.get(ks)==null){
                netStockQ =oldStockMap.get(ks).getStockQuantity();
                netStockV = oldStockMap.get(ks).getStockValue();
            }
            netStock.add(new Stock(ks,netStockQ, netStockV));
        }

        for(Stock ns: netStock){
            System.out.println(ns.getStockCode() +"- Quantity - "+ ns.getStockQuantity()+"- Value -"+ns.getStockValue());
        }
    }
}

---------------输出---------------

1- Quantity - 30- Value -24000
2- Quantity - 10- Value -5000
3- Quantity - 25- Value -5000
5- Quantity - 5- Value -2500

4 个答案:

答案 0 :(得分:5)

您可以执行以下操作(假设您无法升级到Java 8)

  • 创建一个以股票代码为键,股票为价值的地图
Map<Integer, Stock> netStockMap = new HashMap<Integer, Stock>();
  • 然后将所有旧库存条目添加到该地图,如下所示。
for (Stock oldStockItem: oldStock) {
    netStockMap.put(oldStockItem.getStockCode(), oldStockItem);
}
  • 然后针对每个新库存条目,检查地图中是否存在旧条目。如果存在,则创建一个新库存条目,将新旧条目合并。否则,只需将新的库存条目添加到地图即可。
for (Stock newStockItem: newStock) {
    Integer stockCode = newStockItem.getStockCode();
    Stock oldStockItem = netStockMap.get(stockCode);
    if (oldStockItem != null) {
        Stock netStockItem = new Stock(stockCode, oldStockItem.getStockQuantity() + newStockItem.getStockQuantity(),oldStockItem.getStockValue() + newStockItem.getStockValue());
        netStockMap.put(stockCode, netStockItem);

    } else {
        netStockMap.put(stockCode, newStockItem);
    }
}
  • 然后获取地图的值作为最终库存清单
List<Stock> netStock = new ArrayList<Stock>(netStockMap.values());

答案 1 :(得分:4)

如果您可以升级到Java 8,则可以通过Streams有效地实现它。

您可以使用Streams根据ID对这些项目进行分组,然后对它们的值求和,最后将它们收集为以下列表:

List<Stock> netStock = new ArrayList<Stock>(oldStock);
netStock.addAll(newStock);

netStock = new ArrayList<>(netStock.stream().collect(
        Collectors.toMap(Stock::getStockCode, Function.identity(), (Stock i1, Stock i2) -> {
            i1.setStockQuantity(i1.getStockQuantity()+i2.getStockQuantity());
            i1.setStockValue(i1.getStockValue()+i2.getStockValue());
            return i1;
        })).values());

输出:

1- Quantity - 30- Value -24000
2- Quantity - 10- Value -5000
3- Quantity - 25- Value -5000
5- Quantity - 5- Value -2500

还需要为setter类中的字段创建Stock方法

答案 2 :(得分:2)

我宁愿添加StockCollector来减少集合上不必要的迭代,并消除多余的地图和列表。

class StockCollector {

    private Map<Integer, Stock> stockMap = new HashMap<Integer, Stock>();

    public void addStock(List<Stock> stock) {
         for(Stock s: stock) {
             Stock oldStock = stockMap.get(s.getStockCode());
             Integer netStockQ = 0;
             Integer netStockV = 0;
             if(oldStock != null) {
                 netStockQ = oldStock.getStockQuantity() + s.getStockQuantity();
                 netStockV = oldStock.getStockValue() + s.getStockValue();                     
             } else {
                 netStockQ = s.getStockQuantity();
                 netStockV = s.getStockValue();
             }
             stockMap.put(new Stock(s.getStockCode(), netStockQ, netStockV));
         }
    }

    public Collection<Stock> getStock() {
         return stockMap.values();
    }
}

然后您可以根据需要添加任意数量的股票:

StockCollector collector = new StockCollector();
collector.addStock(oldStock);
collector.addStock(newStock);

for(Stock ns: collector.getStock()){
    System.out.println(ns.getStockCode() +"- Quantity - "+ ns.getStockQuantity()+"- Value -"+ns.getStockValue());
}

答案 3 :(得分:1)

我认为您不需要使用正在使用的2张地图(oldStockMap和newStockMap)。您只能使用一个映射,首先要插入一个列表中的所有元素,然后再更新第二个列表中重复的元素,或者添加第二个列表中没有重复的元素。复杂度是相同的,但是有一点点改善。

public class Stock {

    private int stockCode;
    private int stockQuantity;
    private int stockValue;

    public int getStockCode() {
        return stockCode;
    }

    public int getStockQuantity() {
        return stockQuantity;
    }

    public int getStockValue() {
        return stockValue;
    }

    public Stock(int stockCode, int stockQuantity, int stockValue) {
        this.stockCode = stockCode;
        this.stockQuantity = stockQuantity;
        this.stockValue = stockValue;
    }

    public static void main(String[] args){
        List<Stock> oldStock = new ArrayList<Stock>();
        Stock s1 = new Stock(1,  20, 16000);
        Stock s2 = new Stock(2, 10, 5000);
        Stock s3 = new Stock(3,  15, 3000);
        oldStock.add(s1);
        oldStock.add(s2);
        oldStock.add(s3);

        List<Stock> newStock = new ArrayList<Stock>();
        Stock s4 = new Stock(5, 5, 2500);
        Stock s5 = new Stock(1, 10, 8000);
        Stock s6 = new Stock(3, 10, 2000);
        newStock.add(s4);
        newStock.add(s5);
        newStock.add(s6);

        Map<Integer, Stock> netStockMap = new HashMap<Integer, Stock>();

        for(Stock os:oldStock){
            netStockMap.put(os.getStockCode(),os);
        }

        for(Stock ns:newStock){
            Integer code = ns.getStockCode();
            if(netStockMap.get(ns.getStockCode()) != null) {
                Integer netStockQ = netStockMap.get(code).getStockQuantity() + ns.getStockQuantity();
                Integer netStockV = netStockMap.get(code).getStockValue() + ns.getStockValue();
                netStockMap.put(code, new Stock(code, netStockQ, netStockV));
            } else {
                netStockMap.put(code,ns);
            }
        }

        List<Stock> netStock = new ArrayList<Stock>();
        netStock.addAll(netStockMap.values());

        for(Stock ns: netStock){
            System.out.println(ns.getStockCode() +"- Quantity - "+ ns.getStockQuantity()+"- Value -"+ns.getStockValue());
        }
    }
}