poj3349 哈希表的运用

初学哈希表

哈希表(也叫散列表 Hash Table)的思路是根据关键码值直接访问。任何一种数据结构都有它的优势,哈希表提供这么一种其他数据结构并不擅长的操作:在理想情况下,能用常量时间查找到指定值的数据。

题意:有n片雪花,问是否有两片完全相同呢? 雪花都是六棱的,如果六棱的长度对应完全相等,则认为两片雪花相同。
思路:如果两两比较的话,就是n^2算法,肯定要超时的,如果用hash的话,就可以将雪花分类,在同类里再两两比较,由于每一类的规模比较小,如果hash函数写的好的话,就可以很大程度上降低复杂度,这里我用的是六棱之和相等为一类(其实就是同义词),对应同一个散列地址,用的是开散列法。
代码
 
    
1 #include < stdio.h >
2 #include < string .h >
3 #include < string .h >
4 #include < stdlib.h >
5 #include < math.h >
6
7 #include < iostream >
8   using namespace std;
9
10 #define NN 15000 // 14997 + 3
11 #define NL 100
12 #define L 6
13 typedef struct {
14 int a[L];
15 }item;
16
17 item snow[NN][NL];
18 int m[NN];
19
20 int hash(item SNOW){
21 int i;
22 int key = 0 ;
23 for (i = 0 ; i < 6 ; i ++ ){
24 key += SNOW.a[i];
25 }
26 key %= 14997 ;
27 return key;
28 }
29
30 int cmp(item x, item y){
31 int st, i, j;
32 for (st = 0 ; st < 6 ; st ++ ){ // 右移
33 for (i = st, j = 0 ; j < 6 ; j ++ , i = (i + 1 ) % 6 ){
34 if (x.a[i] != y.a[j]) break ;
35 }
36 if (j == 6 ) return 1 ;
37 }
38 for (st = 0 ; st < 6 ; st ++ ){ // 左移
39 for (i = st, j = 0 ; j < 6 ; j ++ , i = (i + 5 ) % 6 ){
40 if (x.a[i] != y.a[j]) break ;
41 }
42 if (j == 6 ) return 1 ;
43 }
44 return 0 ;
45 }
46 int main() {
47 int i, j, pos, n;
48 item SNOW;
49 scanf( " %d " , & n);
50 memset(m, 0 , sizeof (m));
51 for (i = 1 ; i <= n; i ++ ){
52 for (j = 0 ; j < 6 ; j ++ ){
53 scanf( " %d " , & SNOW.a[j]);
54 }
55 pos = hash(SNOW);
56 for (j = 0 ; j < m[pos]; j ++ ){
57 if (cmp(SNOW, snow[pos][j])){
58 puts( " Twin snowflakes found. " );
59 return 0 ;
60 }
61 }
62 snow[pos][m[pos]] = SNOW;
63 m[pos] ++ ;
64 }
65 puts( " No two snowflakes are alike. " );
66 return 0 ;
67 }
68

 

 

转载于:https://www.cnblogs.com/ylfdrib/archive/2010/11/30/1892273.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值