• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*---------------------------------------------------------------------------*
2  *  astar_pphash.c  *
3  *                                                                           *
4  *  Copyright 2007, 2008 Nuance Communciations, Inc.                               *
5  *                                                                           *
6  *  Licensed under the Apache License, Version 2.0 (the 'License');          *
7  *  you may not use this file except in compliance with the License.         *
8  *                                                                           *
9  *  You may obtain a copy of the License at                                  *
10  *      http://www.apache.org/licenses/LICENSE-2.0                           *
11  *                                                                           *
12  *  Unless required by applicable law or agreed to in writing, software      *
13  *  distributed under the License is distributed on an 'AS IS' BASIS,        *
14  *  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. *
15  *  See the License for the specific language governing permissions and      *
16  *  limitations under the License.                                           *
17  *                                                                           *
18  *---------------------------------------------------------------------------*/
19 
20 #include "pstdio.h"
21 #include "passert.h"
22 #include "portable.h"
23 
24 #include"duk_err.h"
25 #include"srec.h"
26 #include"astar.h"
27 #include"astar_pphash.h"
28 
29 #define DEBUG_PPHASH 0
30 
31 
32 /* initialize the hash with no elements defined */
33 
hash_init(FixedSizeHash * hash,srec * rec_debug)34 void hash_init(FixedSizeHash* hash, srec* rec_debug)
35 {
36   int i;
37   hash->hashsize = FSH_HASHSIZE;
38   for (i = 0; i < hash->hashsize; i++)
39     hash->items[i] = FSH_NULL;
40   hash->rec = rec_debug;
41 }
42 
43 /* compare a couple of paths,
44    ie see whether the word history is the same */
45 
compare_parp(partial_path * parp1,partial_path * parp2,srec * rec)46 int compare_parp(partial_path* parp1, partial_path* parp2, srec* rec)
47 {
48   asr_int32_t diff = 0;
49   if (parp1->first_prev_arc != PARP_TERMINAL ||
50       parp2->first_prev_arc != PARP_TERMINAL)
51   {
52     diff = parp1->token_index - parp2->token_index;
53   }
54   else
55   {
56     while (parp1->next && parp2->next)
57     {
58       diff = parp1->word - parp2->word;
59       if (diff)
60       {
61         goto CPE;
62       }
63       parp1 = parp1->next;
64       parp2 = parp2->next;
65     }
66     diff = (intptr_t)parp1->next - (intptr_t)parp2->next;
67   }
68 CPE:
69   if (diff)
70     diff = (diff < 0 ? -1 : 1);
71   return diff;
72 }
73 
74 /* find the bin */
75 
hashfunc(partial_path * parp)76 unsigned int hashfunc(partial_path* parp)
77 {
78   unsigned int hashval;
79   if (parp->first_prev_arc != PARP_TERMINAL)
80     hashval = parp->token_index;
81   else
82     hashval = 0;
83   hashval = (hashval << 10) + parp->word;
84   while ((parp = parp->next) != NULL)
85   {
86     if (parp->word != MAXwordID)
87       hashval = hashval * 64 + parp->word + hashval % 65536;
88   }
89   return hashval;
90 }
91 
92 /* get a history same as this one */
93 
hash_get(FixedSizeHash * hash,partial_path * parp,void ** hval)94 int hash_get(FixedSizeHash* hash, partial_path* parp, void** hval)
95 {
96   unsigned int hkey_index = hashfunc(parp);
97   partial_path* p_return;
98 
99   hkey_index = hkey_index % hash->hashsize;
100   p_return = hash->items[hkey_index];
101   if (!p_return)
102     return FSH_NO_SUCH_KEY;
103   for (; p_return; p_return = p_return->hashlink)
104   {
105     if (compare_parp(p_return, parp, hash->rec) == 0)
106     {
107       *hval = p_return;
108       return FSH_SUCCESS;
109     }
110   }
111   return FSH_NO_SUCH_KEY;
112 }
113 
114 /* set this, return error is same path already there */
115 
hash_set(FixedSizeHash * hash,partial_path * parp)116 int hash_set(FixedSizeHash* hash, partial_path* parp)
117 {
118   unsigned int hkey_index = hashfunc(parp);
119   partial_path** p_insert;
120 
121   hkey_index = hkey_index % hash->hashsize;
122   p_insert = &hash->items[hkey_index];
123   for (; *p_insert; p_insert = &((*p_insert)->hashlink))
124   {
125     if (*p_insert == parp)
126     {
127 #if 1||DEBUG_PPHASH
128       print_path(parp, hash->rec, "problem in astar_pphash hash_set ");
129 #endif
130       return FSH_SUCCESS;
131     }
132     else if (compare_parp(*p_insert, parp, hash->rec) == 0)
133     {
134 #if DEBUG_PPHASH
135       print_path(*p_insert, hash->rec, "key taken in astar_pphash hash_set ");
136 #endif
137       return FSH_KEY_OCCUPIED;
138     }
139   }
140   *p_insert = parp;
141 #if DEBUG_PPHASH
142   printf("setting at %d ", hkey_index);
143   print_path(parp, hash->rec, "");
144 #endif
145   parp->hashlink = FSH_NULL;
146   return FSH_SUCCESS;
147 }
148 
149 /* delete an element */
150 
hash_del(FixedSizeHash * hash,partial_path * parp)151 int hash_del(FixedSizeHash* hash, partial_path* parp)
152 {
153   unsigned int hkey_index = hashfunc(parp);
154   partial_path** p_insert;
155 
156   hkey_index = hkey_index % hash->hashsize;
157   p_insert = &hash->items[hkey_index];
158   for (; *p_insert; p_insert = &((*p_insert)->hashlink))
159   {
160     if (compare_parp(*p_insert, parp, hash->rec) == 0)
161     {
162       *p_insert = parp->hashlink;
163 #if DEBUG_PPHASH
164       printf("delhash at %d\n", hkey_index);
165       print_path(parp, hash->rec, "deleted ");
166 #endif
167       return FSH_SUCCESS;
168     }
169   }
170   return FSH_NO_SUCH_KEY;
171 }
172 
173