算法题解记录-2452距离字典两次编辑以内的单词

[LeetCode 118 / 2452] 距离字典两次编辑以内的单词

题目描述

给你两个字符串数组 queriesdictionary,数组中所有单词都只包含小写英文字母,且长度都相同。

一次编辑操作定义为:将单词中的任意一个字母修改为另一个字母。

请你从 queries 中找出所有这样的单词:它们可以在不超过两次编辑 操作内,变成 dictionary 中的某个单词。

返回结果列表,顺序需与 queries 中的顺序一致。


示例

示例 1
复制代码
输入:
queries = ["word","note","ants","wood"]
dictionary = ["wood","joke","moat"]

输出:["word","note","wood"]

解释:
- "word" → 将 'r' 改为 'o',得到 "wood"(1 次编辑)
- "note" → 将 'n' 改为 'j',将 't' 改为 'k',得到 "joke"(2 次编辑)
- "ants" → 无法在 2 次内得到 dictionary 中的单词
- "wood" → 已经是 dictionary 中的单词(0 次编辑)
示例 2
复制代码
输入:
queries = ["yes"]
dictionary = ["not"]

输出:[]

解释:
"yes" 无法在 2 次编辑内变成 "not"

解题思路

这道题的核心在于判断两个单词是否可以在两次编辑内相等

1. 问题拆解

我们可以将问题分解为三个层次:

  • 最底层 :判断两个单词是否能通过 ≤ 2 次编辑相等(canTransform
  • 中间层 :判断一个单词是否能通过 ≤ 2 次编辑变成字典中任意一个单词isWordValid
  • 最外层 :遍历 queries,收集所有符合条件的单词

2. 判断两个单词是否能在两次编辑内相等

因为所有单词长度相同,我们只需逐位比较:

  • 初始化 diffCount = 0
  • 遍历两个单词的每一位
  • 如果对应位置字符不同,则 diffCount++
  • 如果 diffCount > 2,返回 false
  • 遍历结束后返回 true

这个方法时间复杂度为 O(n),n 为单词长度。

java 复制代码
private boolean canTransform(String s1, String s2) {
    int diff = 0;
    for (int i = 0; i < s1.length(); i++) {
        if (s1.charAt(i) != s2.charAt(i)) {
            diff++;
            if (diff > 2) {
                return false;
            }
        }
    }
    return true;
}

3. 判断一个单词是否与字典中任意单词匹配

遍历字典中的每个单词,调用 canTransform

java 复制代码
private boolean isWordValid(String word, String[] dictionary) {
    for (String dictWord : dictionary) {
        if (canTransform(word, dictWord)) {
            return true;
        }
    }
    return false;
}

4. 主流程

遍历 queries,对每个单词调用 isWordValid,如果为 true 则加入结果列表。

java 复制代码
public List<String> twoEditWords(String[] queries, String[] dictionary) {
    List<String> res = new ArrayList<>();
    for (String q : queries) {
        if (isWordValid(q, dictionary)) {
            res.add(q);
        }
    }
    return res;
}

复杂度分析

  • 时间复杂度:O(q × d × n),其中:
    • q = queries 的长度
    • d = dictionary 的长度
    • n = 单词长度
  • 空间复杂度:O(1),除了结果列表外,只使用了常数空间

总结

这道题属于典型的"模拟 + 逐位比较"类问题,逻辑清晰,适合作为字符串基础练习。关键在于理解"两次编辑"的限制,并将其转化为逐位差异计数的思路。

如果你有更好的解法(比如使用字典树优化),也欢迎在评论区交流!


欢迎关注我的博客,持续更新 LeetCode 题解与算法笔记。

相关推荐
xsyaaaan40 分钟前
leetcode-hot100-双指针:283移动零-11盛最多水的容器-15三数之和-42接雨水
算法·leetcode
一方热衷.3 小时前
YOLO26-Seg ONNXruntime C++/python推理
开发语言·c++·python
炽烈小老头4 小时前
【每天学习一点算法 2026/03/08】相交链表
学习·算法·链表
靓仔建4 小时前
Vue3导入组件出错does not provide an export named ‘user_setting‘ (at index.vue:180:10)
开发语言·前端·typescript
一碗白开水一4 小时前
【工具相关】OpenClaw 配置使用飞书:打造智能飞书助手全流程指南(亲测有效,放心享用)
人工智能·深度学习·算法·飞书
仰泳的熊猫5 小时前
题目2194:蓝桥杯2018年第九届真题-递增三元组
数据结构·c++·算法
Tisfy5 小时前
LeetCode 1888.使二进制字符串字符交替的最少反转次数:前缀和O(1)
算法·leetcode·字符串·题解
赶路人儿5 小时前
UTC时间和时间戳介绍
java·开发语言
6+h5 小时前
【java】基本数据类型与包装类:拆箱装箱机制
java·开发语言·python
bugcome_com5 小时前
C# 事件(Event)详解及实战示例
c#