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

调用方法时如何让LinkedHashMap新增元素的键自增1

问题根因

键始终为1的核心原因是Java基本类型采用值传递机制:

  1. 你在menuItem方法中定义的iTerms、iDef是基本类型局部变量,调用addCard时传入的是这两个值的副本,不是变量本身
  2. addCard方法内部对iTerms、iDef的自增操作,只会修改方法内的副本值,不会影响外层menuItem中的原始变量
  3. 每次调用addCard时,拿到的初始iTerms、iDef都是0,自增后永远是1,所以存入集合的键一直是1

原代码还存在3个隐藏问题:

  • 在addCard中重复创建Scanner实例,和外层输入流冲突,容易出现输入读取错位
  • 如果词汇校验通过存入map后,对应的释义重复,原代码不会回滚已经存入的词汇,会导致两个map的数据长度不匹配
  • 定义LinkedHashMap时没有指定泛型,存在类型安全风险
修复方案

把计数器、Scanner实例、两个存储map都定义为类的成员变量,不要把计数器作为参数传给addCard方法,所有方法直接操作成员变量,就能保留自增状态。
修复后可运行的完整代码如下:

import java.util.LinkedHashMap;
import java.util.Scanner;

public class FlashCardApp {
    // 全局共享的存储集合、计数器、输入实例
    private final LinkedHashMap<Integer, String> terms = new LinkedHashMap<>();
    private final LinkedHashMap<Integer, String> definitions = new LinkedHashMap<>();
    private final Scanner scanner = new Scanner(System.in);
    private int termCount = 0;
    private int defCount = 0;

    public void runMenu() {
        boolean isRunning = true;
        while (isRunning) {
            System.out.println("Input the action (add, remove, import, export, ask, exit):");
            String action = scanner.nextLine();
            switch (action) {
                case "add":
                    addCard();
                    break;
                case "remove":
                    // 自行补全删除逻辑
                    break;
                case "import":
                    // 自行补全导入逻辑
                    break;
                case "export":
                    // 自行补全导出逻辑
                    break;
                case "ask":
                    // 自行补全测试逻辑
                    break;
                case "exit":
                    isRunning = false;
                    System.out.println("Bye bye!");
                    break;
                default:
                    System.out.println("Unknown action");
            }
        }
        scanner.close();
    }

    private void addCard() {
        System.out.println("The card:");
        String term = scanner.nextLine();
        if (terms.containsValue(term)) {
            System.out.println("The card \"" + term + "\" already exists.");
            return;
        }

        // 词汇校验通过,键自增后存入
        int currentTermKey = ++termCount;
        terms.put(currentTermKey, term);

        System.out.println("The definition of the card:");
        String def = scanner.nextLine();
        if (definitions.containsValue(def)) {
            System.out.println("The definition \"" + def + "\" already exists.");
            // 释义重复,回滚已经存入的词汇,保证数据一致
            terms.remove(currentTermKey);
            termCount--;
            return;
        }

        // 释义校验通过,键自增后存入
        definitions.put(++defCount, def);
        System.out.printf("The pair (\"%s\":\"%s\") has been added.%n", term, def);

        // 调试打印,正式使用可删除
        System.out.println("Terms map: " + terms);
        System.out.println("Definitions map: " + definitions);
    }

    public static void main(String[] args) {
        new FlashCardApp().runMenu();
    }
}
修复说明
  • 计数器termCount、defCount作为类成员变量全局唯一,每次自增的状态会被保留,新增元素的键会从1开始连续递增
  • 全局只使用一个Scanner实例读取输入,避免多实例导致的输入流问题
  • 新增了释义重复时的词汇回滚逻辑,保证两个map的键一一对应,不会出现脏数据
  • 给集合加上了明确的泛型定义,消除类型安全警告
  • 不需要提前预知录入总数量,循环会一直运行直到用户输入exit退出,完全匹配需求

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.28 17:12:32