annotate PsiCLASS-1.0.2/BitTable.hpp @ 0:903fc43d6227 draft default tip

Uploaded
author lsong10
date Fri, 26 Mar 2021 16:52:45 +0000
parents
children
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
0
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
1 /**
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
2 Use an 64bit integer to represent bit table.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
3
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
4 Li Song
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
5 July 24, 2012
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
6
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
7 - Modified again from May 27, 2017.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
8 */
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
9
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
10
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
11 #ifndef _BIT_TABLE_HEADER
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
12 #define _BIT_TABLE_HEADER
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
13
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
14 #include <stdio.h>
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
15
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
16 typedef unsigned long long int UINT64 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
17 #define UNIT_SIZE (sizeof( UINT64 ) * 8 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
18 #define UNIT_MASK ((UINT64)63)
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
19
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
20 class BitTable
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
21 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
22 private:
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
23 UINT64 *tab ; // The bits
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
24 int size ; // The size of the table
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
25 int asize ; // The size of the array (size/64).
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
26 public:
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
27 BitTable() // Intialize a bit table.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
28 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
29 //tab = new UINT64[1] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
30 //size = UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
31 tab = NULL ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
32 size = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
33 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
34
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
35 BitTable( int s ) // Initalize a bit table with size s.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
36 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
37 if ( s == 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
38 s = UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
39
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
40 if ( s & UNIT_MASK )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
41 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
42 asize = s / UNIT_SIZE + 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
43 tab = new UINT64[ asize ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
44 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
45 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
46 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
47 asize = s / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
48 tab = new UINT64[ asize ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
49 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
50
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
51 size = s ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
52 Reset() ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
53 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
54
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
55 ~BitTable()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
56 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
57 //printf( "hi %d\n", size ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
58 //printf( "%s\n", __func__ ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
59 //if ( tab != NULL )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
60 // delete [] tab ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
61 //size = -1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
62
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
63 // Manually release the memory.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
64 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
65
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
66 void Init( int s ) // Initialize a bit table with size s.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
67 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
68 if ( tab != NULL )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
69 delete [] tab ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
70
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
71 if ( s == 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
72 s = UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
73
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
74 if ( s & UNIT_MASK )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
75 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
76 asize = s / UNIT_SIZE + 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
77 tab = new UINT64[ asize ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
78 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
79 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
80 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
81 asize = s / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
82 tab = new UINT64[ asize ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
83 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
84
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
85 size = s ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
86 Reset() ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
87 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
88
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
89 void Release()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
90 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
91 if ( tab != NULL )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
92 delete[] tab ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
93 tab = NULL ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
94 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
95
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
96 void Reset() // Make every value 0.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
97 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
98 for ( int i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
99 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
100 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
101
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
102 void Set( int i ) // Set the ith bit.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
103 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
104 int ind, offset ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
105 ind = i / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
106 offset = i & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
107 //printf( "%d,%d %d,%d: %llx", 311 / UNIT_SIZE, 311 & UNIT_MASK, 279 / UNIT_SIZE, 279 & UNIT_MASK, tab[ind] ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
108 tab[ind] |= ( (UINT64)1 << offset ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
109 //printf( " %llx %d\n", tab[ind], UNIT_SIZE ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
110 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
111
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
112 void Unset( int i ) // Unset the ith bit
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
113 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
114 int ind, offset ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
115 ind = i / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
116 offset = i & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
117
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
118 tab[ind] &= ( (UINT64)-1 ^ ( (UINT64)1 << offset ) ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
119 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
120
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
121 void Flip( int i ) // Flip the ith bit. Same as xor 1.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
122 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
123 int ind, offset ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
124 ind = i / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
125 offset = i & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
126
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
127 tab[ind] ^= ( (UINT64)1 << offset ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
128 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
129
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
130 bool Test( unsigned int i ) const // Test the ith bit.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
131 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
132 if ( i >= (unsigned int)size )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
133 return false ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
134
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
135 unsigned int ind, offset ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
136 ind = i / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
137 offset = i & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
138
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
139 if ( tab[ind] & ( (UINT64)1 << offset ) )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
140 return true ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
141 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
142 return false ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
143 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
144
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
145 void Not() // Not all the bits.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
146 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
147 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
148 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
149 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
150 tab[i] = ~tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
151 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
152 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
153
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
154 void And( const BitTable &in ) // Do the "and" on each bits.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
155 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
156 if ( asize != in.asize )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
157 return ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
158 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
159 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
160 tab[i] &= in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
161 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
162
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
163 void Or( const BitTable &in ) // Do the "or" on each bits.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
164 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
165 if ( asize != in.asize )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
166 return ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
167 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
168 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
169 tab[i] |= in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
170 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
171
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
172 void Xor( const BitTable &in )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
173 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
174 if ( asize != in.asize )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
175 return ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
176 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
177 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
178 tab[i] ^= in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
179 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
180
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
181 // Unset all the bits outside [s,e]
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
182 void MaskRegionOutside( unsigned int s, unsigned int e )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
183 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
184 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
185 // mask out [0, s-1].
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
186 int ind, offset ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
187 if ( s > 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
188 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
189 ind = (s - 1) / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
190 offset = ( s - 1 ) & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
191 for ( i = 0 ; i <= ind - 1 ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
192 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
193 if ( offset + 1 >= 64 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
194 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
195 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
196 tab[i] = ( tab[i] >> (UINT64)( offset + 1 ) ) << (UINT64)( offset + 1 ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
197 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
198
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
199 // mask out [e+1, size-1]
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
200 if ( e < ( (unsigned int)size - 1 ) )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
201 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
202 ind = ( e + 1 ) / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
203 offset = ( e + 1 ) & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
204 for ( i = ind + 1 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
205 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
206
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
207 if ( UNIT_SIZE - offset >= 64 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
208 tab[ind] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
209 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
210 tab[ind] = ( tab[ind] << (UINT64)( UNIT_SIZE - offset ) ) >> (UINT64)( UNIT_SIZE - offset ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
211 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
212 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
213
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
214 // Given further information about the position of first and last 1's
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
215 void MaskRegionOutsideInRange( int s, int e, int first, int last )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
216 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
217 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
218 int start, to ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
219 start = first / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
220 to = last / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
221 // mask out [0, s-1].
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
222 int ind, offset ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
223 if ( s > 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
224 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
225 ind = (s - 1) / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
226 offset = ( s - 1 ) & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
227 for ( i = start ; i <= ind - 1 ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
228 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
229 if ( offset + 1 >= 64 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
230 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
231 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
232 tab[i] = ( tab[i] >> (UINT64)( offset + 1 ) ) << (UINT64)( offset + 1 ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
233 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
234
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
235 // mask out [e+1, size-1]
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
236 if ( e < size - 1 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
237 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
238 ind = ( e + 1 ) / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
239 offset = ( e + 1 ) & UNIT_MASK ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
240 for ( i = ind + 1 ; i <= to ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
241 tab[i] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
242
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
243 if ( UNIT_SIZE - offset >= 64 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
244 tab[ind] = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
245 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
246 tab[ind] = ( tab[ind] << (UINT64)( UNIT_SIZE - offset ) ) >> (UINT64)( UNIT_SIZE - offset ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
247 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
248 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
249 void ShiftOneLeft()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
250 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
251 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
252 UINT64 carry = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
253 UINT64 lastTabMask ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
254 if ( ( size & UNIT_MASK ) == 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
255 lastTabMask = (UINT64)(-1) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
256 else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
257 lastTabMask = ( 1 << ( size & UNIT_MASK ) ) - 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
258
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
259 for ( i = 0 ; i < asize - 1 ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
260 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
261 UINT64 tmp = ( tab[i] >> ( UNIT_SIZE - 1 ) ) & 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
262 tab[i] = ( tab[i] << 1 ) | carry ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
263 carry = tmp ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
264 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
265 tab[i] = ( ( tab[i] << 1 ) | carry ) & lastTabMask ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
266 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
267
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
268 void ShiftOneRight()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
269 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
270 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
271 UINT64 carry = ( tab[ asize - 1 ] & 1 ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
272 tab[ asize - 1 ] >>= 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
273 for ( i = asize - 2 ; i >= 0 ; --i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
274 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
275 UINT64 tmp = ( tab[i] & 1 ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
276 tab[i] = ( tab[i] >> 1 ) | ( carry << ( UNIT_SIZE - 1 ) ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
277 carry = tmp ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
278 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
279 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
280
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
281 bool IsAllZero()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
282 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
283 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
284 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
285 if ( tab[i] != 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
286 return false ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
287 return true ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
288 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
289
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
290 int Count() const // Count how many 1.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
291 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
292 if ( size <= 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
293 return 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
294 UINT64 k ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
295 int i, ret = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
296 for ( i = 0 ; i < asize - 1 ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
297 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
298 k = tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
299 while ( k )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
300 //for ( j = 0 ; j < UNIT_SIZE ; ++j )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
301 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
302 if ( k & 1 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
303 ++ret ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
304 //printf( "### %d %d %d %d\n", ret, asize, size, k ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
305 k /= 2 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
306 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
307 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
308 //printf( "(%d) ", ret ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
309 k = tab[ asize - 1 ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
310 for ( i = 0 ; i <= (int)( ( size - 1 ) & UNIT_MASK ) ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
311 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
312 if ( k & 1 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
313 ++ret ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
314 k /= 2 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
315 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
316 //for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
317 // printf( "%llu ", tab[i] ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
318 //printf( "(%d)\n", ret ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
319 return ret ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
320 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
321
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
322 void GetOnesIndices( std::vector<int> &indices )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
323 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
324 if ( size <= 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
325 return ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
326 UINT64 k ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
327 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
328 int ind = 0 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
329 for ( i = 0 ; i < asize - 1 ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
330 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
331 k = tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
332 ind = i * UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
333 while ( k )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
334 //for ( j = 0 ; j < UNIT_SIZE ; ++j )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
335 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
336 if ( k & 1 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
337 indices.push_back( ind ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
338 //printf( "### %d %d %d %d\n", ret, asize, size, k ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
339 k /= 2 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
340 ++ind ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
341 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
342 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
343 //printf( "(%d) ", ret ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
344 k = tab[ asize - 1 ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
345 ind = i * UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
346 for ( i = 0 ; i <= (int)( ( size - 1 ) & UNIT_MASK ) ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
347 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
348 if ( k & 1ull )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
349 indices.push_back( ind ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
350 k /= 2ull ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
351 ++ind ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
352 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
353 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
354
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
355 bool IsEqual( const BitTable &in ) const// Test wether two bit tables equal.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
356 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
357 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
358 if ( in.size != size )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
359 return false ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
360 //printf( "== %d %d\n", in.size, size ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
361 //if ( size & UNIT_MASK )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
362 // k = size / UNIT_SIZE + 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
363 //else
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
364 // k = size / UNIT_SIZE ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
365
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
366 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
367 if ( tab[i] != in.tab[i] )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
368 return false ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
369 return true ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
370 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
371
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
372 // Return the location of the first difference. -1 if the same.
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
373 int GetFirstDifference( const BitTable &in ) const
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
374 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
375 int as = asize < in.asize ? asize : in.asize ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
376 //int s = size < in.size ? size : in.size ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
377 int i, j ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
378
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
379 for ( i = 0 ; i < as ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
380 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
381 if ( tab[i] != in.tab[i] )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
382 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
383 UINT64 k1 = tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
384 UINT64 k2 = in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
385 for ( j = 0 ; j < (int)UNIT_SIZE ; ++j )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
386 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
387 if ( ( k1 & 1 ) != ( k2 & 1 ) )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
388 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
389 return j + UNIT_SIZE * i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
390 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
391 k1 >>= 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
392 k2 >>= 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
393 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
394 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
395 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
396
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
397 for ( ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
398 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
399 if ( tab[i] != 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
400 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
401 UINT64 k = tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
402 for ( j = 0 ; j < (int)UNIT_SIZE ; ++j )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
403 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
404 if ( k & 1 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
405 return j + UNIT_SIZE * i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
406 k >>= 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
407 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
408 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
409 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
410
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
411 for ( ; i < in.asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
412 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
413 if ( in.tab[i] != 0 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
414 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
415 UINT64 k = in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
416 for ( j = 0 ; j < (int)UNIT_SIZE ; ++j )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
417 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
418 if ( k & 1 )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
419 return j + UNIT_SIZE * i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
420 k >>= 1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
421 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
422 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
423 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
424 return -1 ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
425 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
426
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
427 void Duplicate( BitTable &in )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
428 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
429 if ( tab != NULL )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
430 delete [] tab ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
431 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
432 size = in.size ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
433 asize = in.asize ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
434 tab = new UINT64[ asize ] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
435 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
436 tab[i] = in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
437 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
438
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
439 /*void SetBulk( int ind, uint64_t val )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
440 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
441 tab[ind] = val ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
442 }*/
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
443
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
444 void Assign( BitTable &in )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
445 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
446 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
447 for ( i = 0 ; i < asize ; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
448 tab[i] = in.tab[i] ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
449 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
450
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
451 void Nullify()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
452 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
453 tab = NULL ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
454 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
455
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
456 int GetSize()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
457 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
458 return size ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
459 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
460
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
461 void Print()
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
462 {
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
463 int i ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
464 for ( i = 0 ; i < asize; ++i )
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
465 printf( "%llu ", tab[i] ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
466 printf( "\n" ) ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
467 }
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
468 } ;
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
469
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
470
903fc43d6227 Uploaded
lsong10
parents:
diff changeset
471 #endif