题目:
三人行设计了一个灌水论坛。信息学院的学生都喜欢在上面交流灌水,传说在论坛上有一个“水王”,他不但喜欢发帖,还会回复其他ID发的每个帖子。坊间风闻该“水王”发帖数目超过了帖子数目的一半。如果你有一张当前论坛的帖子(包括回帖)列表,其中帖子的作者的ID也在其中,你能快速的找到这个传说中的水王吗?
设计思路:
从ID文件中获得发帖者的ID后开始两两相消,相同的ID保留不相同的全部取消,因为字符串处理起来比较困难,这次我用的数字代替比较简单,这种方法并不适合水王发帖正好比全部数量的帖子多1个帖子,因为最后剩下的那一个并不能确定是不是水王,有可能是用户输入的出现错误,比如,1 2 3和1 2 1,如果用户给出的ID文件错误那么得到的水王就会不准确。
代码如下:
1 #include<iostream> 2 #include<fstream> 3 using namespace std; 4 int waterking(int ID[],int num) 5 { 6 int j=0,k=1; 7 while(k<num) 8 { 9 10 while(ID[j]==-1) 11 { 12 j++; 13 } 14 while(ID[k]==-1) 15 { 16 j++; 17 } 18 while(ID[j]==ID[k]) 19 { 20 k++; 21 } 22 if(ID[j]!=ID[k]&&ID[k]!=-1) 23 { 24 ID[j]=-1; 25 ID[k]=-1; 26 j++; 27 k=j+1; 28 } 29 } 30 return ID[j]; 31 } 32 void main() 33 { 34 ifstream infile("ID.txt"); 35 int ID[1000],i=0,num,wk; 36 infile>>ID[i]; 37 while(ID[i]>0) 38 { 39 i++; 40 infile>>ID[i]; 41 } 42 num=i; 43 cout<<"获得的ID表为:"<<endl; 44 for(i=0;i<num;i++) 45 cout<<ID[i]<<" "; 46 cout<<endl; 47 wk=waterking(ID,num); 48 cout<<"水王的ID是:"<<wk; 49 }
运行结果:
结果分析
这道例题代码不长,主要是考虑应该用什么样的方法实现,要怎样去实现代码的优化。首先要解决的是找到问题解决的核心,这道题中,根据条件我们可以知道,半数以上帖子都是一个ID的,所以,只要找到中间的值,就能找到所谓的水王,但是,这样的优化还不够完美,要将他的时间复杂度降为O(n^2),就要考虑相同ID和不同ID之间的关系,对于不同的ID,直接摒除,那么就可以排除水王的存在,因为水王发帖数足够大,那么最后剩下的肯定是水王。