MathTL
utils/tiny_tools.h
00001 // -*- c++ -*-
00002 
00003 // +--------------------------------------------------------------------+
00004 // | This file is part of MathTL - the Mathematical Template Library    |
00005 // |                                                                    |
00006 // | Copyright (c) 2002-2009                                            |
00007 // | Thorsten Raasch, Manuel Werner                                     |
00008 // +--------------------------------------------------------------------+
00009 
00010 #ifndef _MATHTL_TINY_TOOLS_H
00011 #define _MATHTL_TINY_TOOLS_H
00012 
00013 #include <cassert>
00014 #include <cmath>
00015 #include <functional>
00016 #include <map>
00017 
00018 // some utility functions
00019 
00021 template <class R>
00022 inline R abs(const R a)
00023 {
00024   return  (a > 0 ? a : -a);
00025 }
00026 
00028 template <class R>
00029 inline R sign(const R a)
00030 {
00031   return (a > 0 ? 1. : (a < 0 ? -1. : 0.));
00032 }
00033 
00035 
00042 template <class R>
00043 inline R hypot(const R a, const R b)
00044 {
00045   R r(0);
00046   if (a == 0)
00047     r = abs(b);
00048   else
00049     {
00050       R c(b/a);
00051       r = abs(a) * sqrt(1+c*c);
00052     }
00053   return r;
00054 }
00055 
00057 template <class I>
00058 I factorial(const I n)
00059 {
00060   I r(1);
00061   for (I i(2); i <= n; r *= i, i++);
00062   return r;
00063 }
00064 
00076 inline int binomial(const int n, const int k)
00077 {
00078   int r(1);
00079   
00080   if (k > n || k < 0)
00081     return 0;
00082   
00083   if (k == 0)
00084     return 1;
00085   
00086   for (int i(k+1); i <= n; i++)
00087     r *= i;
00088   
00089   for (int i(2); i+k <= n; i++)
00090     r /= i; // always possible without remainder
00091   
00092   return r;
00093 }
00094 
00096 inline int minus1power(const int k)
00097 {
00098   return (k%2==0 ? 1 : -1);
00099 }
00100 
00102 template <class I, class J>
00103 int intpower(const I n, const J k)
00104 {
00105   int r(1);
00106   for (J j(1); j <= k; j++)
00107     r *= n;
00108 
00109   return r;
00110 }
00111 
00116 template <class I, class C>
00117 class threshold_criterion
00118   : public std::unary_function<I, C>
00119 {
00120 public:
00121   threshold_criterion(const double eta) : eta_(eta) {}
00122   bool operator() (std::pair<const I, C>& p) { return fabs(p.second) < eta_; }
00123 
00124 private:
00125   const double eta_;
00126 };
00127 
00132 inline
00133 double twotothejhalf(const int j)
00134 {
00135   return j%2 ? M_SQRT2 * (1<<(j>>1)) : 1<<(j>>1);
00136 }
00137 
00142 inline
00143 int dyadic_modulo (const int x, const int j)
00144 {
00145   return (x >= 0
00146           ? x-((x>>j)<<j)
00147           : (x+(((-x)>>j)<<j)) ? x+((((-x)>>j)+1)<<j) : 0);
00148 }
00149 
00150 
00151 /*
00152  * computes floor(log2(n)), where n is a positive integer
00153  * Tested for int n, unsigned int n.
00154  * 2.5 times faster than log2(double)
00155  * 
00156  * Be careful with negative arguments and automatic conversion to unsigned int.
00157  * 
00158  * There might be more clever alternatives for this function!
00159  * 
00160  * Assumption: 
00161  * sizeof(int) = sizeof(unsigned int) = 4
00162  * 
00163  * Code borrowed from:
00164  * Bit Twiddling Hacks - http://graphics.stanford.edu/~seander/bithacks.html#IntegerLogLookup
00165  * By Sean Eron Anderson
00166  * seander@cs.stanford.edu 
00167  * (with additions from Andrew Shapira) 
00168  */
00169 const unsigned int log2Bits[] = {0x2, 0xC, 0xF0, 0xFF00, 0xFFFF0000}; //, 0xFFFFFFFF00000000}; // uncomment for 64 bit integers
00170 const unsigned int log2Sizes[] = {1, 2, 4, 8, 16}; //, 32}; // uncomment for 64 bit integers
00171 
00172 inline unsigned int log2(const unsigned int n)
00173 {
00174     unsigned int v;  // 32-bit value to find the log2 of 
00175     v = n;
00176     register unsigned int r = 0; // result of log2(v) will go here
00177     int i;
00178     for (i = 4; i >= 0; i--) // unroll for speed...
00179     {
00180         if (v & log2Bits[i])
00181         {
00182             v >>= log2Sizes[i];
00183             r |= log2Sizes[i];
00184         } 
00185     }
00186     return r;
00187 }
00188 
00189 #endif
 All Classes Functions Variables Typedefs Enumerations