如何遍历 HashMap 的 ArrayList<Double> 值?

How to iterate through ArrayList<Double> values of HashMap?

一个新手的问​​题。对不起。

我有这个 customersOrders HashMap,它将 String 作为键,ArrayList<Double> 作为值。我需要找到每个客户的订单总和以及最大总金额,以便找到最大的客户。我如何设法仅使用嵌套的 For 循环和 HashMap 方法来做到这一点?我完全坚持这一点。

public class Test {

    public static void main(String[] args) {

        HashMap<String, ArrayList<Double>> customersOrders;

        customersOrders = new HashMap<>();
        ArrayList<Double> orders = new ArrayList<>();
        orders.add(55.50);
        orders.add(78.30);
        orders.add(124.75);
        customersOrders.put("John", orders);

        orders = new ArrayList<>();
        orders.add(28.35);
        orders.add(37.40);
        customersOrders.put("Helen", orders);

        orders = new ArrayList<>();
        orders.add(150.10);
        customersOrders.put("Thomas", orders);

        orders = new ArrayList<>();
        orders.add(230.45);
        orders.add(347.20);
        customersOrders.put("Robert", orders);

        orders = new ArrayList<>();
        orders.add(530.25);
        orders.add(325.40);
        orders.add(11550.70);
        orders.add(2480.65);
        customersOrders.put("Jennifer", orders);

        System.out.println(customersOrders);

    }
}

到目前为止,我一直在尝试做这样的事情,但显然没有成功:

double maxOrder = 0;
String customerName = "";

for (ArrayList<Double> orders : customersOrders.values()) {
    for (double orderPrice : orders) {
        if (orderPrice > maxOrder) {
            maxOrder = orderPrice;
        }
    }
}
        
for (String name : customersOrders.keySet()) {
    if (maxOrder.equals(customersOrders.get(name))) {
        customerName = name;
        break;
    }
}

也许是这样的:

        Map<String, Double> customersSum = new HashMap<>();
        Double maxSum = Double.MIN_VALUE;
        String customerWithMaxSum;
        
        for (Map.Entry<String, List<Double>> entry: customersOrders.entrySet()) {
            String customerId = entry.getKey();
            List<Double> customerOrders = entry.getValue();
            
            Double customerSum = customerOrders.stream().mapToDouble(d -> d).sum();
            customersSum.put(customerId, customerSum);
            
            if (customerSum > maxSum) {
                maxSum =  customerSum;
                customerWithMaxSum = customerId;
            }
        }

第二部分也可以使用流 pi:

Optional<String> customerWithMaxSum = customersSum.entrySet()
                .stream()
                .max(Comparator.comparingDouble(Map.Entry::getValue))
                .map(Map.Entry::getKey);

你的逻辑代码不正确

    for (double orderPrice : orders) {
        if (orderPrice > maxOrder) {
            maxOrder = orderPrice;
        }
    }

您不是将价格相加然后与 maxOrder 进行比较,而是将每个价格与 maxOrder 进行比较。这不是您的问题所要求的。

你应该这样做

    double ordersSum = 0;
    for (double orderPrice : orders) {
        ordersSum += orderPrice;
    }
    if (ordersSum > maxOrder) {
        maxOrder = ordersSum;
    }

并且在你的第二个 for 循环中,你将双精度值与数组列表进行比较,这会导致编译错误你应该将每个自定义产品的总和与 maxOrder.

进行比较

我在这里应该注意,这段代码不是很有效,您可以像在第二个循环中那样循环键,然后计算其中的总和并与 maxOrder 进行比较,我将此实现保留为给你一个练习。

您可以创建另一个 HashMap 来保存您的总和,然后找出其中的最大值。

首先遍历所有 HashMap 键并找到每个客户的总和,如下所示:

HashMap<String, ArrayList<Double>> customerOrders = new HashMap<>();
// Fill your HashMap as you've done above

HashMap<String, Double> customerSums = new HashMap<>(); // The new HashMap that keeps the sums

for (String customerName : customerOrders.keySet()) // Foreach customer
{
    double currentSum = 0;
    for (Double aDouble : customerOrders.get(customerName)) 
    {
        currentSum += aDouble; // Sum the orders
    }
    
    customerSums.put(customerName, currentSum); // Put the sum in your new HashMap
    
}

现在找到最大值应该非常简单。尝试这样做 :D

您正在迭代 orders 地图中的值。这不会告诉您与谁相关联。相反,您可以遍历键集或条目集,计算该客户的总和,并将其与 运行 最大值进行比较。由于您指定使用 for-loops,因此以下排除了流 API.

的使用
String maxOrderCustomer = null;
double maxOrder = 0.0;
for (Map.EntrySet<String,List<Double>> entry : customerOrders.entrySet()) {
  Double sum = 0.0;
  for (Double order : entry.getValue();
    sum += order;
  }
  if (order > maxOrder) {
    maxOrder = order;
    maxOrderCustomer = entry.getKey();
  }
}

此时,您将获得金额最大的客户名称和该金额。如果要显示相关的订单列表,可以使用名称从原始Map中拉取列表。