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

如何按通话记录出现频率对包含手机号姓名的Phone列表排序

问题根源

你用HashMap<Phone, Integer>统计次数不准的核心原因是Phone类没有重写equals()和hashCode()方法:HashMap对比key时默认对比对象内存地址,你统计时新创建的Phone对象和PhoneList中存储的Phone对象哪怕手机号完全一致,也会被判定为不同的key,最终统计结果不符合预期。


解决方案

步骤1:改造Phone类,补充必要方法

class Phone {
    private String phoneNum;
    private String name;

    // 保留原有构造方法
    public Phone(String phoneNum, String name) {
        this.phoneNum = phoneNum;
        this.name = name;
    }

    // 补充属性的getter方法
    public String getPhoneNum() {
        return phoneNum;
    }

    public String getName() {
        return name;
    }

    // 重写equals:手机号相同即判定为同一个Phone对象
    @Override
    public boolean equals(Object o) {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;
        Phone phone = (Phone) o;
        return phoneNum.equals(phone.phoneNum);
    }

    // 重写hashCode:用手机号生成哈希值
    @Override
    public int hashCode() {
        return phoneNum.hashCode();
    }
}

同时记得给PhoneList加getPhones()公共方法、CallList加getCalls()公共方法,用于读取内部存储的集合数据。

步骤2:统计次数并排序

这里提供两种实现方案,第二种简化版不需要修改Phone类的equals和hashCode,出错概率更低:

// 简化版实现:直接用手机号作为key统计,不需要修改Phone类
public List<String> getSortedPhoneNumbers(PhoneList phoneList, CallList callList) {
    HashMap<String, Integer> countMap = new HashMap<>();
    // 初始化所有手机号的出现次数为0,避免未出现在通话记录里的手机号被遗漏
    for (Phone phone : phoneList.getPhones()) {
        countMap.put(phone.getPhoneNum(), 0);
    }

    // 遍历通话记录统计次数(主叫、被叫各算一次)
    for (Call call : callList.getCalls()) {
        countMap.put(call.getFrom(), countMap.get(call.getFrom()) + 1);
        countMap.put(call.getTo(), countMap.get(call.getTo()) + 1);
    }

    // 按出现次数降序排序,次数相同则按手机号升序排序,可自行调整排序规则
    List<Phone> sortedPhones = new ArrayList<>(phoneList.getPhones());
    sortedPhones.sort((p1, p2) -> {
        int sortByCount = countMap.get(p2.getPhoneNum()).compareTo(countMap.get(p1.getPhoneNum()));
        if (sortByCount == 0) {
            return p1.getPhoneNum().compareTo(p2.getPhoneNum());
        }
        return sortByCount;
    });

    // 提取排序后的手机号列表作为输出结果
    List<String> result = new ArrayList<>();
    for (Phone phone : sortedPhones) {
        result.add(phone.getPhoneNum());
    }
    return result;
}

其他优化建议

你读取Calls.txt的代码里不需要自行创建新的Phone对象存到Call实例中,建议Call类的from、to属性直接存字符串类型的手机号即可,减少冗余对象和匹配错误概率。

内容的提问来源于stack exchange,提问作者Hoàng Huy

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.09.27 21:36:03