zoukankan      html  css  js  c++  java
  • 动物统计 (Hash)

    描述

    在美丽大兴安岭原始森林中存在数量繁多的物种,在勘察员带来的各种动物资料中有未统计数量的原始动物的名单。科学家想判断这片森林中哪种动物的数量最多,但是由于数据太过庞大,科学家终于忍受不了,想请聪明如你的ACMer来帮忙。
     
    输入
    第一行输入动物名字的数量N(1<= N <= 4000000),接下来的N行输入N个字符串表示动物的名字(字符串的长度不超过10,字符串全为小写字母,并且只有一组测试数据)。
    输出
    输出这些动物中最多的动物的名字与数量,并用空格隔开(数据保证最多的动物不会出现两种以上)。
    样例输入
    10
    boar
    pig
    sheep
    gazelle
    sheep
    sheep
    alpaca
    alpaca
    marmot
    mole
    样例输出
    sheep 3
    数据量太大,用map显然会超时,用Hash可以过(还有其他方法,这里只谈Hash)。

     首先得找个字符串Hash函数,听说BKDRHash非常高效,就拿来用了,至于原理希望路过的大牛指点。确实不知道!

     然后用链地址法处理冲突就OK了,动态更新最大值。

    我的代码:

    #include<stdio.h>
    #include<string.h>
    #include<malloc.h>
    #define N 4300000
    
    typedef struct node
    {
      char ch[11];//存放动物名称 
      int cnt;//计数器        
      struct node *next;
    } Animal;
    
    Animal a[N];
    unsigned int BKDRHash(char *str);//一个很高效的字符串Hash函数 
    Animal * search(Animal an[],int n , char *str);
    void insert(Animal an[],int n ,char *str);
    
    int main()
    {
      Animal *temp;
      int n,i,id,max;
      char t[11];  
      scanf("%d",&n);
      getchar();
      
       max = 1;
       for(i = 0 ; i < n ; ++i)
       {
          char c[11];
          scanf("%s",c);
          insert(a,N,c); 
          temp = search(a,N,c);
          if(temp->cnt > max)
          {
            max = temp->cnt ;
            strcpy(t,temp->ch);            
          } 
       }
       printf("%s %d\n",t,max);
         
      //system("pause");
      return 0;    
    }
    
    /* 这个函数是借用,我也看不太懂,希望懂的高手指点下 */ 
    unsigned int BKDRHash(char *str)
    {
    	unsigned int seed = 131; // 31 131 1313 13131 131313 etc..
    	unsigned int hash = 0;
     
    	while (*str)
    	{
    		hash = hash * seed + (*str++);
    	}
     
    	return (hash & 0x7FFFFFFF) % N;
    }
    
    Animal * search(Animal an[],int n , char *str)
    {
       Animal *p;
       int pos;
       pos = BKDRHash(str);
       p = &an[pos];
       while(p && strcmp(p->ch,str) )//查找    
       p = p->next;
       return p;//如果为NULL,则表示没找到。  
    }
    
    void insert(Animal an[],int n ,char *str)
    {
       Animal *p,*one;
       int pos;
       p = search(an,n,str);
       if(p)
       {
          ++(p->cnt);//找到了,计数器加 1     
       }    
       else//没找到,就插入 
       {
         pos = BKDRHash(str);
         one = (Animal *)malloc(sizeof(Animal));
         strcpy(one->ch,str);
         one->cnt = 1;//新来的,计数器置 1    
         one->next = an[pos].next; 
         an[pos].next = one; 
       } 
         
    }
    
  • 相关阅读:
    SoapUI 使用笔记
    git 使用笔记(二)
    git 使用笔记(一)
    jquery 拓展
    hdu 1024 Max Sum Plus Plus (DP)
    hdu 2602 Bone Collector (01背包)
    hdu 1688 Sightseeing (最短路径)
    hdu 3191 How Many Paths Are There (次短路径数)
    hdu 2722 Here We Go(relians) Again (最短路径)
    hdu 1596 find the safest road (最短路径)
  • 原文地址:https://www.cnblogs.com/HpuAcmer/p/2281348.html
Copyright © 2011-2022 走看看