20240113-确定两个字符串是否接近

题目要求

如果可以使用以下操作从另一个字符串获得一个字符串,则认为两个字符串是接近的:

  • 操作1:交换任意两个现有字符。 例如,abcde -> aecdb
  • 操作2:将每个出现的一个现有字符转换为另一个现有字符,并对另一个字符执行相同操作。 例如,aacabb -> bbcbaa(所有a都变成b,所有b都变成a)

您可以根据需要多次对任一字符串使用这些操作。 给定两个字符串,word1 和 word2,如果 word1 和 word2 接近,则返回 true,否则返回 false。

Example 1:

复制代码
Input: word1 = "abc", word2 = "bca"
Output: true
Explanation: You can attain word2 from word1 in 2 operations.
Apply Operation 1: "abc" -> "acb"
Apply Operation 1: "acb" -> "bca"

Example 2:

复制代码
Input: word1 = "a", word2 = "aa"
Output: false
Explanation: It is impossible to attain word2 from word1, or vice versa, in any number of operations.

Example 3:

复制代码
Input: word1 = "cabbba", word2 = "abbccc"
Output: true
Explanation: You can attain word2 from word1 in 3 operations.
Apply Operation 1: "cabbba" -> "caabbb"
Apply Operation 2: "caabbb" -> "baaccc"Apply Operation 2: "baaccc" -> "abbccc"

思路

两个字符串相似的定义是"通过无限的操作能够互相得到 ",因此我们似乎并不需要记住字母的顺序,只需要记住字母出现的次数即可。用到哈希表

  • 操作1:交换任意两个现有字符。 例如,abcde -> aecdb

很明显操作1中的操作并不改变字母的数量,但是可以1对1操作字母顺序。因此只要两个字符串每个字母出现的数量一致,都可以通过操作1互相转换。

  • 操作2:将每个出现的一个现有字符转换为另一个现有字符,并对另一个字符执行相同操作。 例如,aacabb -> bbcbaa(所有a都变成b,所有b都变成a)

操作2,交换不同字母的个数,也就是说我们甚至不需要准确的记录每个对应每个字母出现的次数,只要记录出现次数的list能对应上就可以。(但是统计个数也需要用哈希表来完成)

另外在获得map1和map2之后还需要判断一下二者的键是否都匹配,因为不存在的字母之间是无法互相转换的。

代码

cpp 复制代码
class Solution {
public:
    bool closeStrings(string word1, string word2) {
        map<char, int> map1, map2;
        if (word1.size() != word2.size()) {
            return false;
        }
        for (int i = 0; i < word1.size(); ++i) {
            map1[word1[i]] += 1;
            map2[word2[i]] += 1;
        }
        
        for (auto &p : map1) {
            if (map2.find(p.first) == map2.end()) return false;
        }
        for (auto &p : map2) {
            if (map1.find(p.first) == map1.end()) return false;
        }

        vector<int> values1, values2;
        for (auto &p : map1) values1.push_back(p.second);
        for (auto &p : map2) values2.push_back(p.second);

        sort(values1.begin(), values1.end());
        sort(values2.begin(), values2.end());

        return values1 == values2;
    }
};

时间复杂度

  • 映射字符: O(N),其中 N 是字符串的长度。

  • 检查字符是否存在: O(N),假设映射操作为 O(log N),且最多有 N 个唯一字符。

  • 排序频率: O(N log N),因为频率排序最差也要对 N 个元素进行排序。

  • 总体时间复杂度 O(N log N),主要是排序步骤。

空间复杂度

  • 频率计数映射: O(N),用于存储字符频率。
  • 频率向量: O(N),用于存储频率的两个向量。
  • 整体空间复杂度:O(N) O(N),因为所用空间与唯一字符数成正比,最多为 N。
相关推荐
SweetCode几秒前
裴蜀定理:整数解的奥秘
数据结构·python·线性代数·算法·机器学习
ゞ 正在缓冲99%…14 分钟前
leetcode76.最小覆盖子串
java·算法·leetcode·字符串·双指针·滑动窗口
xuanjiong15 分钟前
纯个人整理,蓝桥杯使用的算法模板day2(0-1背包问题),手打个人理解注释,超全面,且均已验证成功(附带详细手写“模拟流程图”,全网首个
算法·蓝桥杯·动态规划
惊鸿.Jh34 分钟前
【滑动窗口】3254. 长度为 K 的子数组的能量值 I
数据结构·算法·leetcode
明灯L34 分钟前
《函数基础与内存机制深度剖析:从 return 语句到各类经典编程题详解》
经验分享·python·算法·链表·经典例题
碳基学AI40 分钟前
哈尔滨工业大学DeepSeek公开课:探索大模型原理、技术与应用从GPT到DeepSeek|附视频与讲义免费下载方法
大数据·人工智能·python·gpt·算法·语言模型·集成学习
补三补四44 分钟前
机器学习-聚类分析算法
人工智能·深度学习·算法·机器学习
独好紫罗兰1 小时前
洛谷题单3-P5718 【深基4.例2】找最小值-python-流程图重构
开发语言·python·算法
正脉科工 CAE仿真1 小时前
基于ANSYS 概率设计和APDL编程的结构可靠性设计分析
人工智能·python·算法
爱喝热水的呀哈喽1 小时前
Java 集合 Map Stream流
数据结构