static int wing=[]()
{
std::ios::sync_with_stdio(false);
cin.tie(NULL);
return ;
}(); class Solution
{
public:
string mostCommonWord(string paragraph, vector<string>& banned)
{
unordered_map<string,int> simap;
for(string s:banned)
simap[s]=-;
int beg=,flag=,max=;
paragraph.push_back(' ');
string res;
int sz=paragraph.length();
for(int i=;i<sz;i++)
{
if(isalpha(paragraph[i]))
paragraph[i]=tolower(paragraph[i]);
else if(paragraph[i]!=' ')
{
flag=;
continue;
}
else
{
string cur=paragraph.substr(beg,i-flag-beg);
simap[cur]++;
beg=i+;
flag=;
if(simap[cur]>max)
{
res=cur;
max=simap[cur];
}
}
}
return res;
}
};
以空格为标志,进行操作。
先把禁止序列扫进map,并将对应的字符串计数器置为-1000,由于段落最长就为1000,这样在扫描段落之后,禁止序列的字符串计数器就不可能为正数,就不会影响到非禁止序列高频单词的筛选。
观察段落序列可以发现,除了首个单词,每个单词前面都是空格,所以我们以空格为判定依据。
遇到字母时,操作只将字母转为小写
遇到非空格非字母,即遇到标点符号时,将标志位置为1,表示在下一个空格前有一个标点符号
遇到空格时,i 代表了空格的下标,beg代表了当前单词序列开始下标,即当前单词的第一个字母下标,用substr将单词提取出来,提取长度为 i-flag-1-beg+1=i-flag-beg
提取出来之后,将单词放入map,并增加计数器,然后比较计数器的值和最大值,进行相应操作。
操作之后,要将beg置为新单词的第一个字母,即i+1,将flag标志置为0。
这里还要注意一点,最后一个单词是以句号结尾的,末尾没有空格,循环不会操作最后一个单词,所以,为了让操作进行完整,在循环前,在段落后面补充了一个空格。
这个题用到了一点技巧性的东西,活用标志位,补充原字符串。