开启掘金成长之旅!这是我参与「掘金日新计划 · 2 月更文挑战」的第 1 天,点击查看活动详情
新年的第一篇水文
刷题的日常-2023年2月1号
一天一题,保持脑子清爽
解密消息
来自leetcode的 2325 题,题意如下:
给你字符串 key 和 message ,分别表示一个加密密钥和一段加密消息。解密 message 的步骤如下:
1、使用 key 中 26 个英文小写字母第一次出现的顺序作为替换表中的字母 顺序 。</br> 2、将替换表与普通英文字母表对齐,形成对照表。</br> 3、按照对照表 替换 message 中的每个字母。</br> 4、空格 ' ' 保持不变。</br>
- 例如,key = "happy boy"(实际的加密密钥会包含字母表中每个字母 至少一次),据此,可以得到部分对照表('h' -> 'a'、'a' -> 'b'、'p' -> 'c'、'y' -> 'd'、'b' -> 'e'、'o' -> 'f')。
返回解密后的消息。
理解题意
通过题意,我们可以将信息整理如下:
- 题目给出两个字符串
- 一个是key,代表映射关系
- 一个是message,代表需要通过映射关系来求解的字符串
- 要求我们将key中第一次出现的字符作为新的映射关系,将message中的字符进行替换
- 题目保证26个字母都有映射关系
- 要求我们返回解密后的字符串
做题思路
根据题目的描述,我们可以构建对应的映射关系之后进行替换即可,步骤如下:
- 开辟一个数组作为最终替换结果
- 开辟一个布尔数组保存是否出现过记录
- 再开辟一个数组用来保存映射关系
- 循环填入数组里的每个字符
- 需要注意的是,key 和 message中都存在 空格,所以需要进行特殊判断
- 最终将message中的字母进行映射即可
代码实现
代码实现如下:
public class Solution {
public String decodeMessage(String key, String message) {
char[] res = new char[message.length()];
boolean[] appearMap = new boolean[26];
char[] charMap = new char[26];
int idx = 0, c;
for (int i = 0; i < charMap.length; i++) {
while ((c = key.charAt(idx++) - 'a') < 0 || appearMap[c]) {}
charMap[c] += i + 'a';
appearMap[c] = true;
}
for (int i = 0; i < message.length(); i++) {
c = message.charAt(i);
if (c == ' ') {
res[i] = ' ';
continue;
}
res[i] = charMap[c - 'a'];
}
return new String(res);
}
}