黑客语(Leet)是从网络发展起来的一种文字书写方式。通常将英语中的字母替换为数字和特殊符号。这种方式被很多黑客组织所使用。由于具有隐密性,所以它也广泛被用于密码中。使用Leet书写的密码,不会增加密码记忆的复杂度,但却可以提高密码的强度。常见的转化规律有,$替换s,3替换e,4替换a,0替换o,1替换i等。例如,cats使用Leet书写,就变为c47$。一个纯字母的密码就转化为字母、数字构成的复杂密码了。 table = ''.maketrans(before, after),这条语句可以创建映射表,str1.translate(table)语句可以将table中的字符按映射表中的顺序进行替换。 替换表如下: 0 1 3 4 5 6 7 o i e a s g t 写一个程序,用于破解一个加密的字符串。M4k3 G006l3 Y0ur H0m3p463! 输入格式 输入一个加密后的字符串 输出格式 输出破解后的字符串
时间: 2024-04-21 12:27:51 浏览: 14
以下是Python实现的代码:
```python
before = "0134567"
after = "oieasgt"
table = str.maketrans(before, after)
encrypted_str = input()
decrypted_str = encrypted_str.translate(table)
print(decrypted_str)
```
输入加密后的字符串,程序会根据替换表将其解密并输出结果。
相关问题
给定一个字符串s,s中只包含数字,请返回s中最长的特殊的回文子串的长度 特殊的回文子串t满足 ·t进行任何次交换后可以变成一个回文字符申 输入格式 输入第一行包含一个字符串s。 数据范围 1s≤10^5 输出格式 特殊的回文子串的最长长度
思路:字符串中只包含数字,那么可行的特殊的回文子串就只有两种,一种是全是同一个数字,一种是只有一个数字出现了奇数次,其他数字都出现了偶数次。因此,我们可以统计每个数字出现的次数,并且记录出现奇数次的数字的个数,最后根据这两个信息来确定最长的特殊回文子串的长度。
具体实现时,由于字符串长度可能非常长,使用桶来统计每个数字出现的次数。同时使用一个计数器 cnt 统计出现奇数次的数字个数。最后,如果 cnt=0,则说明字符串中只有同一个数字,返回字符串长度即可;如果 cnt>1,则说明字符串中不可能存在特殊回文子串,返回 0;否则,字符串中存在特殊回文子串,子串的长度为字符串长度减去奇数数字出现次数减去最后一个奇数数字出现次数。
时间复杂度
统计数字出现次数需要遍历整个字符串,时间复杂度为 O(n),而遍历一遍桶,时间复杂度最多为 O(10),因此总时间复杂度为 O(n)。
C++ 代码
class Solution {
public:
int longestSpecialSubstr(string s) {
vector<int> cnt(10);
for (char c : s) {
++cnt[c - '0'];
}
int odd_cnt = 0;
for (int i : cnt) {
odd_cnt += i & 1;
}
if (odd_cnt == 0) {
return s.size();
} else if (odd_cnt > 1) {
return 0;
}
int n = s.size();
int len = n - odd_cnt;
for (int i = 0, j = n - 1; i < j; ) {
if (cnt[s[i] - '0'] % 2 == 0) {
++i;
--len;
} else if (cnt[s[j] - '0'] % 2 == 0) {
--j;
--len;
} else {
if (s[i] == s[j]) {
len -= 2;
} else {
--len;
}
++i;
--j;
}
}
return len;
}
};
作者:LeetCode-Solution
链接:https://leetcode-cn.com/problems/longest-special-substring/solution/zui-chang-te-shu-hui-wen-zi-chuan-by-leet-tqhx/
来源:力扣(LeetCode)
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。
使用kotlin解决这个问题:139. 单词拆分 中等 2.1K 相关企业 给你一个字符串 s 和一个字符串列表 wordDict 作为字典。请你判断是否可以利用字典中出现的单词拼接出 s 。 注意:不要求字典中出现的单词全部都使用,并且字典中的单词可以重复使用。 示例 1: 输入: s = "leetcode", wordDict = ["leet", "code"] 输出: true 解释: 返回 true 因为 "leetcode" 可以由 "leet" 和 "code" 拼接成。 示例 2: 输入: s = "applepenapple", wordDict = ["apple", "pen"] 输出: true 解释: 返回 true 因为 "applepenapple" 可以由 "apple" "pen" "apple" 拼接成。 注意,你可以重复使用字典中的单词。 示例 3: 输入: s = "catsandog", wordDict = ["cats", "dog", "sand", "and", "cat"] 输出: false 提示: 1 <= s.length <= 300 1 <= wordDict.length <= 1000 1 <= wordDict[i].length <= 20 s 和 wordDict[i] 仅有小写英文字母组成 wordDict 中的所有字符串 互不相同
可以使用动态规划来解决这个问题。首先我们定义一个布尔数组 dp,其中 dp[i] 表示字符串 s 的前 i 个字符是否可以被空格拆分成若干个字典中出现的单词。对于每个 i,我们需要枚举 s 的前 j (j < i) 个字符是否可以拆分成单词,如果可以拆分,那么我们就需要判断 s[j+1,i] 是否出现在字典中,如果出现,则 dp[i] 可以从 dp[j] 转移而来,即 dp[i] = dp[j] && check(s[j+1,i]),其中 check(s[j+1,i]) 表示子串 s[j+1,i] 是否出现在字典中。
具体实现可以参考下面的 Kotlin 代码:
```kotlin
fun wordBreak(s: String, wordDict: List<String>): Boolean {
val n = s.length
val dp = BooleanArray(n + 1)
dp[0] = true // 空串可以被拆分成若干个字典中出现的单词
for (i in 1..n) {
for (j in 0 until i) {
if (dp[j] && wordDict.contains(s.substring(j, i))) {
dp[i] = true
break
}
}
}
return dp[n]
}
```
在上面的代码中,我们使用了 List 的 contains 方法来判断一个字符串是否出现在字典中。如果字典中元素较多,可以考虑使用 Set 或 Map 来优化查询效率。