Grafalgo
Library of useful data structures and algorithms
/Users/jst/src/grafalgo/cpp/dataStructures/heaps/Dheap.cpp
Go to the documentation of this file.
00001 
00009 #include "Dheap.h"
00010 
00011 #define p(x) (((x)+(d-2))/d)
00012 #define left(x) (d*((x)-1)+2)
00013 #define right(x) (d*(x)+1)
00014 
00015 namespace grafalgo {
00016 
00021 Dheap::Dheap(int size, int dd) : Adt(size), d(dd) {
00022         makeSpace(size);
00023 }
00024 
00026 Dheap::~Dheap() { freeSpace(); }
00027 
00031 void Dheap::makeSpace(int size) {
00032         try {
00033                 h = new index[size+1]; pos = new int[size+1];
00034                 kee = new keytyp[size+1];
00035         } catch (std::bad_alloc e) {
00036                 stringstream ss;
00037                 ss << "makeSpace:: insufficient space for "
00038                    << size << "index values";
00039                 string s = ss.str();
00040                 throw OutOfSpaceException(s);
00041         }
00042         for (int i = 1; i <= size; i++) pos[i] = 0;
00043         h[0] = pos[0] = 0; kee[0] = 0;
00044         hn = 0; nn = size;
00045 }
00046 
00048 void Dheap::freeSpace() { delete [] h; delete [] pos; delete [] kee; }
00049 
00051 void Dheap::copyFrom(const Dheap& source) {
00052         if (&source == this) return;
00053         if (source.n() > n()) resize(source.n());
00054         else clear();
00055         d = source.d;
00056         for (int p = 1; p <= source.hn; p--) {
00057                 index x = source.h[p];
00058                 h[p] = x; pos[x] = p; kee[x] = source.key(x);
00059         }
00060 }
00061 
00066 void Dheap::resize(int size) {
00067         freeSpace();
00068         try { makeSpace(size); } catch(OutOfSpaceException e) {
00069                 string s; s = "Dheap::resize::" + e.toString(s);
00070                 throw OutOfSpaceException(s);
00071         }
00072 }
00073 
00078 void Dheap::expand(int size) {
00079         if (size <= n()) return;
00080         Dheap old(this->n(),d); old.copyFrom(*this);
00081         resize(size); this->copyFrom(old);
00082 }
00083 
00085 void Dheap::clear() {
00086         for (int x = 1; x <= hn; x++) pos[h[x]] = 0;
00087         hn = 0;
00088 }
00089 
00094 void Dheap::insert(index i, keytyp k) {
00095         kee[i] = k; hn++; siftup(i,hn);
00096 }
00097 
00101 void Dheap::remove(index i) {
00102         int j = h[hn--];
00103         if (i != j) {
00104                 if (kee[j] <= kee[i]) siftup(j,pos[i]);
00105                 else siftdown(j,pos[i]);
00106         }
00107         pos[i] = 0;
00108 }
00109 
00115 void Dheap::siftup(index i, int x) {
00116         int px = p(x);
00117         while (x > 1 && kee[i] < kee[h[px]]) {
00118                 h[x] = h[px]; pos[h[x]] = x;
00119                 x = px; px = p(x);
00120         }
00121         h[x] = i; pos[i] = x;
00122 }
00123 
00129 void Dheap::siftdown(index i, int x) {
00130         int cx = minchild(x);
00131         while (cx != 0 && kee[h[cx]] < kee[i]) {
00132                 h[x] = h[cx]; pos[h[x]] = x;
00133                 x = cx; cx = minchild(x);
00134         }
00135         h[x] = i; pos[i] = x;
00136 }
00137 
00144 int Dheap::minchild(int x) {
00145         int y; int minc = left(x);
00146         if (minc > hn) return 0;
00147         for (y = minc + 1; y <= right(x) && y <= hn; y++) {
00148                 if (kee[h[y]] < kee[h[minc]]) minc = y;
00149         }
00150         return minc;
00151 }
00152 
00157 void Dheap::changekey(index i, keytyp k) {
00158         keytyp ki = kee[i]; kee[i] = k;
00159         if (k == ki) return;
00160         if (k < ki) siftup(i,pos[i]);
00161         else siftdown(i,pos[i]);
00162 }
00163 
00168 string& Dheap::toString(string& s) const {
00169         stringstream ss;
00170         for (int i = 1; i <= hn; i++) {
00171                 ss << "(" << item2string(h[i],s) << "," << kee[h[i]] << ") ";
00172                 if ((i%10) == 0) s += "\n";
00173         }
00174         if ((hn%10) != 0) s += "\n";
00175         s = ss.str();
00176         return s;
00177 }
00178 
00179 } // ends namespace
 All Classes Files Functions Variables Typedefs Friends