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

如何正确编写Map<Map<String,Item>,Int>中元素计数的自增代码?

解决嵌套Map实现物品计数器的代码问题

原代码的核心问题

  1. 类型转换错误:Pair(i.Name, i) as Map<String, Item>完全不成立,Pair和Map是完全不同的类型,强制转换会直接抛出ClassCastException。
  2. 使用不可变Map:mapOf()创建的是不可变Map,无法执行修改、添加操作,必须改用mutableMapOf()。
  3. 键的匹配逻辑无效:即使能创建Map作为键,每次循环新建的Map对象(内容相同但引用不同)会导致containsKey()永远无法匹配已存在的键(除非依赖Map的内容相等判断,但这种方式冗余且低效)。

正确实现方案

方案一:直接用Item作为键(推荐)

如果Item类正确实现了equals()和hashCode()(比如基于Name或其他唯一标识属性),直接用Item作为键是最简洁高效的方式:

  1. 初始化代码:
var Items = mutableMapOf<Item, Int>()
  1. 计数逻辑代码:
for (item in items) {
    // 简化写法:用getOrPut自动处理存在/不存在的情况
    this.UnitInventory.Items.getOrPut(item) { 0 }++
}

或者用更直观的判断写法:

for (item in items) {
    val count = this.UnitInventory.Items[item] ?: 0
    this.UnitInventory.Items[item] = count + 1
}

方案二:坚持用Map<String, Item>作为键(不推荐)

如果一定要保留原设计思路,需要正确创建Map对象,同时使用可变Map:

  1. 初始化代码:
var Items = mutableMapOf<Map<String, Item>, Int>()
  1. 计数逻辑代码:
for (item in items) {
    val key = mapOf(item.Name to item)
    // 用getOrPut简化逻辑
    this.UnitInventory.Items.getOrPut(key) { 0 }++
}

或者用判断写法:

for (item in items) {
    val key = mapOf(item.Name to item)
    if (this.UnitInventory.Items.containsKey(key)) {
        this.UnitInventory.Items[key] = this.UnitInventory.Items[key]!! + 1
    } else {
        this.UnitInventory.Items[key] = 1
    }
}

关键说明

  • getOrPut是Kotlin提供的便捷函数,会先检查键是否存在:存在则返回对应值,不存在则执行lambda初始化值并添加到Map中,非常适合这种计数场景。
  • 优先选择方案一,因为用Item作为键更符合语义,避免冗余的Map包装,同时性能更优。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.12 18:40:38