2351. 第一次出现两次的字母
题目链接:
自己的做法:
class Solution {
public:
char repeatedCharacter(string s) {
int n = s.size();
vector<int> v(28);
vector<pair<char,int> > p;
for (int i = 0; i < s.size(); i++) {
int j = s[i] - 'a';
v[j]++;
if (v[j] == 2) p.push_back({s[i], i});
}
sort(p.begin(), p.end(), [&](pair<char,int> &a, pair<char,int> &b) {return a.second < b.second;});
return p[0].first;
}
};
更优解:
用二进制数 \(\rm letter26\) 表示出现过的所有字母的集合, \(\rm letter26\) 的从低到高第 \(x\) 位是 \(1\) 表示第 \(x\) 个字母出现过,\(0\) 则表示第 \(x\) 个字母未出现过。
从左到右遍历字符串,对于遍历到的每个字符 \(i\),得到字符 \(i\) 对应的字母编号 \(j\),计算 \(\rm bits=2^j\),执行如下操作:
- 若 \(\rm bits\) & \(\rm letter26\) == \(0\),则当前字符是第一次出现,将 \(\rm letter26\) 的值更新为 \(\rm letter26 | bits\)
- 否则的话当前字符是第二次出现,将当前字符作为答案返回
class Solution {
public:
char repeatedCharacter(string s) {
int letter26 = 0;
for (auto i : s) {
int j = i - 'a';
int bits = 1 << j;
if ((bits & letter26) == 0) {
letter26 = letter26 | bits;
}
else return i;
}
return 'a';//unreachable
}
};

浙公网安备 33010602011771号