1. 题目
给出一系列键盘输入,问是否有坏键。
2. 代码
- 使用一个非法字符加在str后面,就可以判断前后字母是否相等,很方便。
- 设置两个布尔数组,一个假设是坏键,一个确定不是坏键。只要有一次正确输入就可以确定不是坏键。
2.1 自己代码 (有点繁琐
#include <iostream>
#include <string>
#include <vector>
using namespace std;
const int maxn = 1010;
int main() {
//freopen("input.txt", "r", stdin);
int K;
string str;
cin >> K;
cin.ignore();
getline(cin, str);
str = str + '*'; //str后加一个控制字符
bool sure_not_broken[128] = {false}; //确定不是坏键
bool is_broken[128] = {false}; //假设是坏键
int broken_cnt[128] = {0}; //坏键出现次数
vector<char> broken_order;
for (int i = 1; i < str.size(); ++i) {
if (str[i] == str[i - 1]) { //前一个和后一个字符相等,计数
broken_cnt[str[i - 1]]++;
} else { //如果前一个和后一个不一样
broken_cnt[str[i - 1]]++;
if (broken_cnt[str[i - 1]] % K != 0) { //没有到达k次,可以确定不是坏键
sure_not_broken[str[i - 1]] = true;
broken_cnt[str[i - 1]] = 0;
} else {//达到K次,先假设是坏键
is_broken[str[i - 1]] = true;
broken_order.push_back(str[i - 1]);
broken_cnt[str[i - 1]] = 0; //重新计数
}
}
}
bool is_count[128] = {false};
for (int i = 0; i < broken_order.size(); ++i) {
if (is_broken[broken_order[i]] && !sure_not_broken[broken_order[i]]) { //如果确定是坏键,输出
if (!is_count[broken_order[i]]) {
printf("%c", broken_order[i]);
is_count[broken_order[i]] = true;
}
}
}
printf("\n");
string ans;
str.erase(str.end() - 1);
for (int i = 0; i < str.size(); ++i) {
if (sure_not_broken[str[i]]) {
ans += str[i];
} else {
ans += str[i];
i += K - 1;
}
}
printf("%s\n", ans.c_str());
return 0;
}
2.2 柳神代码 (更简洁
#include <iostream>
#include <map>
#include <string>
#include <set>
using namespace std;
bool is_broken[128] = {false};
bool sure_no_broken[256] = {false};
set<char> need_print;
int main() {
int n;
string str;
cin >> n;
cin >> str;
char pre = '@'; //pre表示当前字符的前一个字符
int cnt = 1;
for (int i = 0; i < str.size(); i++) {
if (str[i] == pre) { //如果当前字符和前一个字符一样,cnt++
cnt++;
} else { //不一样
if (cnt % n != 0) { //如果未达到损坏的次数 确信没坏设置为true 就算后面出现达到损坏的次数也不作数
sure_no_broken[pre] = true;
}
cnt = 1; //重置为1
}
is_broken[str[i]] = (cnt % n == 0); //是否坏掉
pre = str[i]; //前往下一个字符
}
for (int i = 0; i < str.size(); i++) {
if (sure_no_broken[str[i]]) { //如果确信没坏
is_broken[str[i]] = false; //坏掉置false
}
}
for (int i = 0; i < str.size(); i++) {
if (is_broken[str[i]] && need_print.find(str[i]) == need_print.end()) { //如果坏掉且未输出
printf("%c", str[i]);
need_print.insert(str[i]);
}
}
printf("\n");
for (int i = 0; i < str.length(); i++) { //输出没坏的剩余字符
printf("%c", str[i]);
if (is_broken[str[i]])
i = i + n - 1;
}
return 0;
}