SHOGUN
v2.0.0
|
00001 /* 00002 * This program is free software; you can redistribute it and/or modify 00003 * it under the terms of the GNU General Public License as published by 00004 * the Free Software Foundation; either version 3 of the License, or 00005 * (at your option) any later version. 00006 * 00007 * Written (W) 2009 Soeren Sonnenburg 00008 * Copyright (C) 2009 Fraunhofer Institute FIRST and Max Planck Society 00009 */ 00010 00011 #ifndef __DYNINT_H__ 00012 #define __DYNINT_H__ 00013 00014 #include <shogun/lib/common.h> 00015 #include <shogun/io/SGIO.h> 00016 #include <shogun/mathematics/Math.h> 00017 00018 namespace shogun 00019 { 00036 template <class T, int sz> class CDynInt 00037 { 00038 public: 00043 CDynInt() 00044 { 00045 for (int i=0; i<sz; i++) 00046 integer[i]=0; 00047 } 00048 00055 CDynInt(uint8_t x) 00056 { 00057 for (int i=0; i<sz-1; i++) 00058 integer[i]=0; 00059 integer[sz-1]= (T) x; 00060 } 00061 00068 CDynInt(uint16_t x) 00069 { 00070 for (int i=0; i<sz-1; i++) 00071 integer[i]=0; 00072 integer[sz-1]= (T) x; 00073 } 00074 00081 CDynInt(uint32_t x) 00082 { 00083 for (int i=0; i<sz-1; i++) 00084 integer[i]=0; 00085 integer[sz-1]= (T) x; 00086 } 00087 00094 CDynInt(int32_t x) 00095 { 00096 for (int i=0; i<sz-1; i++) 00097 integer[i]=0; 00098 integer[sz-1]= (T) x; 00099 } 00100 00107 CDynInt(int64_t x) 00108 { 00109 for (int i=0; i<sz-1; i++) 00110 integer[i]=0; 00111 integer[sz-1]=(T) x; 00112 } 00113 00120 CDynInt(uint64_t x) 00121 { 00122 for (int i=0; i<sz-1; i++) 00123 integer[i]=0; 00124 integer[sz-1]=(T) x; 00125 } 00126 00133 CDynInt(const T x[sz]) 00134 { 00135 for (int i=0; i<sz; i++) 00136 integer[i]=x[i]; 00137 } 00138 00140 CDynInt(const CDynInt<T,sz> &x) 00141 { 00142 for (int i=0; i<sz; i++) 00143 integer[i]=x.integer[i]; 00144 } 00145 00147 ~CDynInt() 00148 { 00149 } 00150 00154 CDynInt<T,sz>& operator=(const CDynInt<T,sz>& x) 00155 { 00156 for (int i=0; i<sz; i++) 00157 integer[i]=x.integer[i]; 00158 return *this; 00159 } 00160 00165 const CDynInt<T,sz> operator|(const CDynInt<T,sz>& x) const 00166 { 00167 CDynInt<T,sz> r; 00168 00169 for (int i=sz-1; i>=0; i--) 00170 r.integer[i]=integer[i] | x.integer[i]; 00171 00172 return r; 00173 } 00174 00179 const CDynInt<T,sz> operator&(const CDynInt<T,sz>& x) const 00180 { 00181 CDynInt<T,sz> r; 00182 00183 for (int i=sz-1; i>=0; i--) 00184 r.integer[i]=integer[i] & x.integer[i]; 00185 00186 return r; 00187 } 00188 00195 CDynInt<T,sz> operator<<(int shift) 00196 { 00197 CDynInt<T,sz> r=*this; 00198 00199 while (shift>0) 00200 { 00201 int s=CMath::min(shift, 8*((int) sizeof(T))-1); 00202 00203 for (int i=0; i<sz; i++) 00204 { 00205 T overflow=0; 00206 if (i<sz-1) 00207 overflow = r.integer[i+1] >> (sizeof(T)*8 - s); 00208 r.integer[i]= (r.integer[i] << s) | overflow; 00209 } 00210 00211 shift-=s; 00212 } 00213 00214 return r; 00215 } 00216 00223 CDynInt<T,sz> operator>>(int shift) 00224 { 00225 CDynInt<T,sz> r=*this; 00226 00227 while (shift>0) 00228 { 00229 int s=CMath::min(shift, 8*((int) sizeof(T))-1); 00230 00231 for (int i=sz-1; i>=0; i--) 00232 { 00233 T overflow=0; 00234 if (i>0) 00235 overflow = (r.integer[i-1] << (sizeof(T)*8 - s)); 00236 r.integer[i]= (r.integer[i] >> s) | overflow; 00237 } 00238 00239 shift-=s; 00240 } 00241 00242 return r; 00243 } 00244 00249 const CDynInt<T,sz> operator^(const CDynInt<T,sz>& x) const 00250 { 00251 CDynInt<T,sz> r; 00252 00253 for (int i=sz-1; i>=0; i--) 00254 r.integer[i]=integer[i] ^ x.integer[i]; 00255 00256 return r; 00257 } 00258 00263 const CDynInt<T,sz> operator+(const CDynInt<T,sz> &x) const 00264 { 00265 CDynInt<T,sz> r; 00266 00267 T overflow=0; 00268 for (int i=sz-1; i>=0; i--) 00269 { 00270 r.integer[i]=integer[i]+x.integer[i]+overflow; 00271 if (r.integer[i] < CMath::max(integer[i], x.integer[i])) 00272 overflow=1; 00273 else 00274 overflow=0; 00275 } 00276 00277 return x; 00278 } 00279 00284 const CDynInt<T,sz> operator-(const CDynInt<T,sz> &x) const 00285 { 00286 return NULL; 00287 } 00288 00293 const CDynInt<T,sz> operator/(const CDynInt<T,sz> &x) const 00294 { 00295 return NULL; 00296 } 00297 00302 const CDynInt<T,sz> operator*(const CDynInt<T,sz> &x) const 00303 { 00304 return NULL; 00305 } 00306 00311 CDynInt<T,sz>& operator+=(const CDynInt<T,sz> &x) 00312 { 00313 return NULL; 00314 } 00315 00320 CDynInt<T,sz>& operator-=(const CDynInt<T,sz> &x) 00321 { 00322 return NULL; 00323 } 00324 00329 CDynInt<T,sz>& operator*=(const CDynInt<T,sz> &x) 00330 { 00331 return NULL; 00332 } 00333 00338 CDynInt<T,sz>& operator/=(const CDynInt<T,sz> &x) 00339 { 00340 return NULL; 00341 } 00342 00347 bool operator==(const CDynInt<T,sz> &x) const 00348 { 00349 for (int i=sz-1; i>=0; i--) 00350 { 00351 if (integer[i]!=x.integer[i]) 00352 return false; 00353 } 00354 00355 return true; 00356 } 00357 00362 bool operator>=(const CDynInt<T,sz> &x) const 00363 { 00364 for (int i=0; i<sz; i++) 00365 { 00366 if (integer[i]>x.integer[i]) 00367 return true; 00368 if (integer[i]<x.integer[i]) 00369 return false; 00370 } 00371 return true; 00372 } 00373 00378 bool operator<=(const CDynInt<T,sz> &x) const 00379 { 00380 for (int i=0; i<sz; i++) 00381 { 00382 if (integer[i]<x.integer[i]) 00383 return true; 00384 if (integer[i]>x.integer[i]) 00385 return false; 00386 } 00387 return true; 00388 } 00389 00394 bool operator>(const CDynInt<T,sz> &x) const 00395 { 00396 for (int i=0; i<sz; i++) 00397 { 00398 if (integer[i]>x.integer[i]) 00399 return true; 00400 if (integer[i]<x.integer[i]) 00401 return false; 00402 } 00403 return false; 00404 } 00405 00410 bool operator<(const CDynInt<T,sz> &x) const 00411 { 00412 for (int i=0; i<sz; i++) 00413 { 00414 if (integer[i]<x.integer[i]) 00415 return true; 00416 if (integer[i]>x.integer[i]) 00417 return false; 00418 } 00419 return false; 00420 } 00421 00426 bool operator!=(const CDynInt<T,sz> &x) const 00427 { 00428 for (int i=sz-1; i>=0; i--) 00429 { 00430 if (integer[i]!=x.integer[i]) 00431 return true; 00432 } 00433 return false; 00434 } 00435 00442 CDynInt<T,sz>& operator|=(const CDynInt<T,sz>& x) 00443 { 00444 for (int i=sz-1; i>=0; i--) 00445 integer[i]|=x.integer[i]; 00446 00447 return *this; 00448 } 00449 00456 CDynInt<T,sz>& operator&=(const CDynInt<T,sz>& x) 00457 { 00458 for (int i=sz-1; i>=0; i--) 00459 integer[i]&=x.integer[i]; 00460 00461 return *this; 00462 } 00463 00470 CDynInt<T,sz>& operator^=(const CDynInt<T,sz>& x) 00471 { 00472 for (int i=sz-1; i>=0; i--) 00473 integer[i]^=x.integer[i]; 00474 00475 return *this; 00476 } 00477 00484 CDynInt<T,sz>& operator<<=(int shift) 00485 { 00486 *this=*this<<shift; 00487 return *this; 00488 } 00489 00496 CDynInt<T,sz>& operator>>=(int shift) 00497 { 00498 *this=*this>>shift; 00499 return *this; 00500 } 00501 00503 CDynInt<T,sz>& operator~() 00504 { 00505 for (int i=sz-1; i>=0; i--) 00506 integer[i]= ~integer[i]; 00507 return *this; 00508 } 00509 00511 operator T() { return integer[sz-1]; } 00512 00514 CDynInt<T,sz>& operator--() 00515 { 00516 T overflow=0; 00517 for (int i=sz-1; i>=0; i--) 00518 { 00519 T x = integer[i]-1-overflow; 00520 overflow=0; 00521 if (integer[i]>x) 00522 overflow=1; 00523 integer[i]=x; 00524 } 00525 return *this; 00526 } 00527 00529 CDynInt<T,sz>& operator++() 00530 { 00531 T overflow=0; 00532 for (int i=sz-1; i>=0; i--) 00533 { 00534 T x = integer[i]+1+overflow; 00535 overflow=0; 00536 if (integer[i]>x) 00537 overflow=1; 00538 integer[i]=x; 00539 } 00540 return *this; 00541 } 00542 00544 void print_hex() const 00545 { 00546 for (int i=0; i<sz; i++) 00547 SG_SPRINT("%.16llx", (uint64_t) integer[i]); 00548 } 00549 00551 void print_bits() const 00552 { 00553 CMath::display_bits(integer, sz); 00554 } 00555 00556 private: 00558 T integer[sz]; 00559 }; 00560 00563 00565 typedef CDynInt<uint64_t,3> uint192_t; 00566 00568 typedef CDynInt<uint64_t,4> uint256_t; 00569 00571 typedef CDynInt<uint64_t,8> uint512_t; 00572 00574 typedef CDynInt<uint64_t,16> uint1024_t; 00576 } 00577 #endif // __DYNINT_H__