You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Java实习生求助:如何用BigDecimal类型Map扣减BigDecimal变量值

解决BigDecimal类型Map值扣减仓库可用量的问题

核心逻辑说明

因为BigDecimal是不可变类,所有运算操作都会返回新的BigDecimal对象,无法直接修改原对象的值。所以扣减仓库可用量的核心是:遍历订单所需的原料条目,取出仓库中对应原料的当前值,执行扣减运算后,将新值重新存入仓库Map。

场景代码实现

假设核心类定义如下(简化版):

// 产品类型枚举
enum ProductType {
    FLOUR, CHEESE, TOMATO_SAUCE, PEPPERONI
}

// 订单原料数量类(数值为BigDecimal类型)
class Quantity {
    private BigDecimal amount;

    public Quantity(BigDecimal amount) {
        this.amount = amount;
    }

    public BigDecimal getAmount() {
        return amount;
    }
}

以下是扣减仓库可用量的核心方法:

import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.Map;

public class WarehouseService {
    // 仓库存储:键为原料类型,值为当前可用量(BigDecimal)
    private Map<ProductType, BigDecimal> warehouse;

    public WarehouseService(Map<ProductType, BigDecimal> warehouse) {
        this.warehouse = warehouse;
    }

    /**
     * 根据披萨订单的原料需求,扣减仓库对应原料的可用量
     * @param pizzaIngredients 披萨所需的原料及对应数量
     * @throws IllegalArgumentException 原料不存在或库存不足时抛出异常
     */
    public void deductIngredients(Map<ProductType, Quantity> pizzaIngredients) {
        for (Map.Entry<ProductType, Quantity> entry : pizzaIngredients.entrySet()) {
            ProductType ingredientType = entry.getKey();
            BigDecimal requiredAmount = entry.getValue().getAmount();

            // 检查仓库中是否存在该原料
            BigDecimal currentStock = warehouse.get(ingredientType);
            if (currentStock == null) {
                throw new IllegalArgumentException("仓库无此原料:" + ingredientType);
            }

            // 检查原料库存是否充足(BigDecimal比较必须用compareTo,不能用equals)
            if (currentStock.compareTo(requiredAmount) < 0) {
                throw new IllegalArgumentException("原料" + ingredientType + "库存不足,当前:" + currentStock + ",需:" + requiredAmount);
            }

            // 执行扣减,按业务需求设置精度与舍入模式(示例保留2位小数,四舍五入)
            BigDecimal newStock = currentStock.subtract(requiredAmount).setScale(2, RoundingMode.HALF_UP);

            // 将扣减后的新库存放回仓库
            warehouse.put(ingredientType, newStock);
        }
    }
}

关键注意事项

  • 不可变性处理:必须用subtract()返回的新BigDecimal对象替换仓库中原有的值,直接修改原对象无效
  • 数值比较:BigDecimal的大小比较要用compareTo()方法,equals()会同时比较值和精度,易导致判断错误
  • 异常与空值处理:根据业务需求选择抛出异常、返回错误提示或降级处理,避免空指针或库存负数
  • 精度控制:通过setScale()指定小数位数和舍入模式,防止计算精度丢失或出现不符合业务要求的数值
  • 并发安全:多线程环境下建议使用ConcurrentHashMap作为仓库容器,或给方法加同步锁,避免并发修改导致数据不一致

内容的提问来源于stack exchange,提问作者Veselin Zahariev

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.20 17:45:46