ZenLib
int128u.h
Go to the documentation of this file.
00001 /*  Copyright (c) MediaArea.net SARL. All Rights Reserved.
00002  *
00003  *  Use of this source code is governed by a zlib-style license that can
00004  *  be found in the License.txt file in the root of the source tree.
00005  */
00006 
00007 //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
00008 //
00009 // based on http://Tringi.Mx-3.cz
00010 // Only adapted for ZenLib:
00011 // - .hpp --> .h
00012 // - Namespace
00013 // - int128u alias
00014 //
00015 //+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
00016 
00017 #ifndef UINT128_HPP
00018 #define UINT128_HPP
00019 
00020 /*
00021   Name: uint128.hpp
00022   Copyright: Copyright (C) 2005, Jan Ringos
00023   Author: Jan Ringos, http://Tringi.Mx-3.cz
00024 
00025   Version: 1.1
00026 */
00027 
00028 
00029 #include <exception>
00030 #include <cstdlib>
00031 #include <cstdio>
00032 #include "ZenLib/Conf.h"
00033 
00034 // CLASS
00035 
00036 namespace ZenLib
00037 {
00038 
00039 class uint128 {
00040     public://private:
00041         // Binary correct representation of signed 128bit integer
00042         int64u lo;
00043         int64u hi;
00044 
00045     protected:
00046         // Some global operator functions must be friends
00047         friend bool operator <  (const uint128 &, const uint128 &) throw ();
00048         friend bool operator == (const uint128 &, const uint128 &) throw ();
00049         friend bool operator || (const uint128 &, const uint128 &) throw ();
00050         friend bool operator && (const uint128 &, const uint128 &) throw ();
00051 
00052     public:
00053         // Constructors
00054         inline uint128 () throw () {};
00055         inline uint128 (const uint128 & a) throw () : lo (a.lo), hi (a.hi) {};
00056 
00057         inline uint128 (const int & a) throw () : lo (a), hi (0ull) {};
00058         inline uint128 (const unsigned int & a) throw () : lo (a), hi (0ull) {};
00059         inline uint128 (const int64u & a) throw () : lo (a), hi (0ull) {};
00060 
00061         uint128 (const float a) throw ();
00062         uint128 (const double & a) throw ();
00063         uint128 (const long double & a) throw ();
00064 
00065         uint128 (const char * sz) throw ();
00066 
00067         // TODO: Consider creation of operator= to eliminate
00068         //       the need of intermediate objects during assignments.
00069 
00070     private:
00071         // Special internal constructors
00072         uint128 (const int64u & a, const int64u & b) throw ()
00073             : lo (a), hi (b) {};
00074 
00075     public:
00076         // Operators
00077         bool operator ! () const throw ();
00078 
00079         uint128 operator - () const throw ();
00080         uint128 operator ~ () const throw ();
00081 
00082         uint128 & operator ++ ();
00083         uint128 & operator -- ();
00084         uint128 operator ++ (int);
00085         uint128 operator -- (int);
00086 
00087         uint128 & operator += (const uint128 & b) throw ();
00088         uint128 & operator *= (const uint128 & b) throw ();
00089 
00090         uint128 & operator >>= (unsigned int n) throw ();
00091         uint128 & operator <<= (unsigned int n) throw ();
00092 
00093         uint128 & operator |= (const uint128 & b) throw ();
00094         uint128 & operator &= (const uint128 & b) throw ();
00095         uint128 & operator ^= (const uint128 & b) throw ();
00096 
00097         // Inline simple operators
00098         inline const uint128 & operator + () const throw () { return *this; };
00099 
00100         // Rest of inline operators
00101         inline uint128 & operator -= (const uint128 & b) throw () {
00102             return *this += (-b);
00103         };
00104         inline uint128 & operator /= (const uint128 & b) throw () {
00105             uint128 dummy;
00106             *this = this->div (b, dummy);
00107             return *this;
00108         };
00109         inline uint128 & operator %= (const uint128 & b) throw () {
00110             this->div (b, *this);
00111             return *this;
00112         };
00113 
00114         // Common methods
00115         unsigned int toUint () const throw () {
00116             return (unsigned int) this->lo; };
00117         int64u toUint64 () const throw () {
00118             return (int64u) this->lo; };
00119         const char * toString (unsigned int radix = 10) const throw ();
00120         float toFloat () const throw ();
00121         double toDouble () const throw ();
00122         long double toLongDouble () const throw ();
00123 
00124         // Arithmetic methods
00125         uint128  div (const uint128 &, uint128 &) const throw ();
00126 
00127         // Bit operations
00128         bool    bit (unsigned int n) const throw ();
00129         void    bit (unsigned int n, bool val) throw ();
00130 }
00131 #ifdef __GNUC__
00132     __attribute__ ((__aligned__ (16), __packed__))
00133 #endif
00134 ;
00135 
00136 
00137 // GLOBAL OPERATORS
00138 
00139 bool operator <  (const uint128 & a, const uint128 & b) throw ();
00140 bool operator == (const uint128 & a, const uint128 & b) throw ();
00141 bool operator || (const uint128 & a, const uint128 & b) throw ();
00142 bool operator && (const uint128 & a, const uint128 & b) throw ();
00143 
00144 // GLOBAL OPERATOR INLINES
00145 
00146 inline uint128 operator + (const uint128 & a, const uint128 & b) throw () {
00147     return uint128 (a) += b; };
00148 inline uint128 operator - (const uint128 & a, const uint128 & b) throw () {
00149     return uint128 (a) -= b; };
00150 inline uint128 operator * (const uint128 & a, const uint128 & b) throw () {
00151     return uint128 (a) *= b; };
00152 inline uint128 operator / (const uint128 & a, const uint128 & b) throw () {
00153     return uint128 (a) /= b; };
00154 inline uint128 operator % (const uint128 & a, const uint128 & b) throw () {
00155     return uint128 (a) %= b; };
00156 
00157 inline uint128 operator >> (const uint128 & a, unsigned int n) throw () {
00158     return uint128 (a) >>= n; };
00159 inline uint128 operator << (const uint128 & a, unsigned int n) throw () {
00160     return uint128 (a) <<= n; };
00161 
00162 inline uint128 operator & (const uint128 & a, const uint128 & b) throw () {
00163     return uint128 (a) &= b; };
00164 inline uint128 operator | (const uint128 & a, const uint128 & b) throw () {
00165     return uint128 (a) |= b; };
00166 inline uint128 operator ^ (const uint128 & a, const uint128 & b) throw () {
00167     return uint128 (a) ^= b; };
00168 
00169 inline bool operator >  (const uint128 & a, const uint128 & b) throw () {
00170     return   b < a; };
00171 inline bool operator <= (const uint128 & a, const uint128 & b) throw () {
00172     return !(b < a); };
00173 inline bool operator >= (const uint128 & a, const uint128 & b) throw () {
00174     return !(a < b); };
00175 inline bool operator != (const uint128 & a, const uint128 & b) throw () {
00176     return !(a == b); };
00177 
00178 
00179 // MISC
00180 
00181 typedef uint128 __uint128;
00182 
00183 typedef uint128 int128u;
00184 } //NameSpace
00185 
00186 #endif