一 :题目
新浪微博可以在发言中嵌入“话题”,即将发言中的话题文字写在一对“#”之间,就可以生成话题链接,点击链接可以看到有多少人在跟自己讨论相同或者相似的话题。新浪微博还会随时更新热门话题列表,并将最热门的话题放在醒目的位置推荐大家关注。
本题目要求实现一个简化的热门话题推荐功能,从大量英文(因为中文分词处理比较麻烦)微博中解析出话题,找出被最多条微博提到的话题。
输入格式:
输入说明:输入首先给出一个正整数N(≤10
5
),随后N行,每行给出一条英文微博,其长度不超过140个字符。任何包含在一对最近的#中的内容均被认为是一个话题,输入保证#成对出现。
输出格式:
第一行输出被最多条微博提到的话题,第二行输出其被提到的微博条数。如果这样的话题不唯一,则输出按字母序最小的话题,并在第三行输出And k more …,其中k是另外几条热门话题的条数。输入保证至少存在一条话题。
注意:两条话题被认为是相同的,如果在去掉所有非英文字母和数字的符号、并忽略大小写区别后,它们是相同的字符串;同时它们有完全相同的分词。输出时除首字母大写外,只保留小写英文字母和数字,并用一个空格分隔原文中的单词。
输入样例:
4
This is a #test of topic#.
Another #Test of topic.#
This is a #Hot# #Hot# topic
Another #hot!# #Hot# topic
输出样例:
Hot
2
And 1 more ...
二:思路分析
思路:想办法将# #中的数据提取出来,然后用map容器进行存储m[str] +=1;如果出现相同的话题
那就加一,(没有重复的m[str]是默认为 0 的也就是最后的m[str] == 1)
接下来map容器当中最后一个值就是最大的当然可能会出现重复的但没关系,我们再根据已知
的最大值即可求取,然后相同话题的个数也就是 题目要求输出的第二项
这里我用的是set容器将每条为微博中的话题提取出来
还有需要注意的是 这道题不是让统计话题的个数最多的,是看每一条微博里提到的话题 ,无论一条微博里提到几次,都统计为这一条微博出现的话题。
三:上码
/**思路:想办法将# #中的数据提取出来,然后用map容器进行存储m[str] +=1;如果出现相同的话题那就加一,(没有重复的m[str]是默认为 0 的也就是最后的m[str] == 1)接下来map容器当中最后一个值就是最大的当然可能会出现重复的但没关系,我们再根据已知的最大值即可求取,然后相同话题的个数也就是 题目要求输出的第二项这里我用的是set容器将每条为微博中的话题提取出来*/#include<bits/stdc++.h>
using namespace std;set<string>s[100010];
set<string>:: iterator st; //提取字符串中# #中间的内容
void deal(string str,int x){int flag = 0; int count = 0;string word = "";//字符串初始化string str1 = "";str += "!";//给字符串末尾加个结束标志 for( int i = 0; i < str.size(); i++ ){//This is a #test of topic#.if( str[i] == '#'){flag = 1;count++;if( i < str.size() - 1)i++;}if( isalpha(str[i]) && flag == 1 || isdigit(str[i]) && flag == 1){//判断该字符是否为字母 || 数字 if( isalpha(str[i])) word += tolower(str[i]);//将大写英文字母改为小写英文字母 if( isdigit(str[i]))word += str[i]; }else if( flag == 1 ) {//这里flag = 1 保证取出的字符为##里头的// cout << word << endl;if( word != " ") str1 += word;word = " ";//清理掉上次的单词存入新的单词 (并且给除第一个单词外的其他单词加上空格)}//代表一个话题里的热点 if( count == 2){flag = 0;count = 0;//可能一行中有多个#号if(str1 != " " )s[x].insert(str1);word = ""; //当一条语句当中,会有两遍热点话题,那么的话(因为在最后执行完str1后 word又被赋值为" ",而新的热点开头需要的是无空格)str1.clear(); }} } int main(){int N;map<string,int>m2;map<string,int>::iterator t; cin >> N; getchar();for( int i = 0; i < N; i++ ){string str;getline(cin,str);deal(str,i);for( st = s[i].begin(); st != s[i].end(); st++ ){m2[*st] += 1; }} // cout << "******************"<< endl;int max = 0; for( t = m2.begin(); t != m2.end(); t++ ){if( t->second > max ){max = t->second;} }// cout << max << endl;int num; for( t = m2.begin(); t != m2.end(); t++ ){if( t->second == max ){string str = t->first;str[0] = toupper(str[0]);cout << str << endl;cout << t->second << endl;num = t->second;break;} }int count = -1;//把自己先排除掉 for( t = m2.begin(); t != m2.end(); t++ ){if(t->second == num )count++;}//cout << m2.size() << endl;if( count > 0)cout << "And " << count << " more ...";} //4
//This is a #test of topic#.
////This is a #Hot# #Hot# topic
//Another #hot!# #Hot# topic//1
//This is a #test of topic#.//1
//Another #hot!# #Hot# topic//Another #Hot# topic//4
//This is a #test of topic#.
//Another #Test of topic.# #Hot#
//This is a #Hot# #Hot# topic
//Another #hot!# #Hot# topic//
//Another #Test1 of topic.#
//This is a #test of topic#.//Another #hot!# #Hot# topic
四:总结
最后有一个点有刚开始一直段错误,那是因为我上方set开的范围太小了,加大范围,比题目的10的5次方大就行 加油boy!
五:知识速递(如果对map容器和set容器不熟悉的兄弟们来这里学习一下哈)
map的基本用法
set的基本用法