node.cpp
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038 #include <gecode/support.hh>
00039 #include <gecode/gist/node.hh>
00040 #include <gecode/gist/visualnode.hh>
00041 #include <cassert>
00042
00043 namespace Gecode { namespace Gist {
00044
00045 Node::~Node(void) {
00046 switch (getTag()) {
00047 case UNDET:
00048 case LEAF:
00049 return;
00050 case TWO_CHILDREN:
00051 delete static_cast<VisualNode*>(getPtr());
00052 if (Support::marked(c.secondChild))
00053 delete static_cast<VisualNode*>(Support::unmark(c.secondChild));
00054 break;
00055 case MORE_CHILDREN:
00056 for (int i=c.noOfChildren; i--;)
00057 delete static_cast<VisualNode**>(getPtr())[i];
00058 heap.free<Node*>(static_cast<Node**>(getPtr()),c.noOfChildren);
00059 }
00060 }
00061
00062 void
00063 Node::setNumberOfChildren(unsigned int n) {
00064 assert(getTag() == UNDET);
00065 switch (n) {
00066 case 0:
00067 setTag(LEAF);
00068 break;
00069 case 1:
00070 setTag(TWO_CHILDREN);
00071 c.secondChild = NULL;
00072 break;
00073 case 2:
00074 setTag(TWO_CHILDREN);
00075 c.secondChild = static_cast<Node*>(Support::mark(NULL));
00076 break;
00077 default:
00078 c.noOfChildren = n;
00079 childrenOrFirstChild = heap.alloc<Node*>(n);
00080 Node** children = static_cast<Node**>(childrenOrFirstChild);
00081 setTag(MORE_CHILDREN);
00082 for (unsigned int i=n; i--;)
00083 children[i] = NULL;
00084 }
00085 }
00086
00087 void
00088 Node::setChild(unsigned int n, Node* child) {
00089 assert(getNumberOfChildren() > n);
00090 if (getTag() == TWO_CHILDREN) {
00091 if (n == 0) {
00092 unsigned int tag = getTag();
00093 childrenOrFirstChild = child;
00094 setTag(tag);
00095 } else {
00096 c.secondChild = static_cast<Node*>(Support::mark(child));
00097 }
00098 } else {
00099 static_cast<Node**>(getPtr())[n] = child;
00100 }
00101 child->parent = this;
00102 }
00103
00104 void
00105 Node::addChild(Node* child) {
00106 child->parent = this;
00107
00108 unsigned int newNoOfChildren = 0;
00109 switch (getTag()) {
00110 case UNDET:
00111 setNumberOfChildren(1);
00112 newNoOfChildren = 1;
00113 break;
00114 case LEAF:
00115 setTag(TWO_CHILDREN);
00116 c.secondChild = NULL;
00117 newNoOfChildren = 1;
00118 break;
00119 case TWO_CHILDREN:
00120 if (Support::marked(c.secondChild)) {
00121 Node** newChildren = heap.alloc<Node*>(c.noOfChildren+1);
00122 newChildren[0] = static_cast<Node*>(getPtr());
00123 newChildren[1] = static_cast<Node*>(Support::unmark(c.secondChild));
00124 newNoOfChildren = 3;
00125 } else {
00126 c.secondChild = static_cast<Node*>(Support::mark(NULL));
00127 newNoOfChildren = 2;
00128 }
00129 break;
00130 case MORE_CHILDREN:
00131 {
00132 Node** newChildren = heap.alloc<Node*>(c.noOfChildren+1);
00133 Node** children = static_cast<Node**>(getPtr());
00134 for (unsigned int i=c.noOfChildren; i--;)
00135 newChildren[i] = children[i];
00136 heap.free<Node*>(children,c.noOfChildren);
00137 childrenOrFirstChild = newChildren;
00138 setTag(MORE_CHILDREN);
00139 c.noOfChildren++;
00140 newNoOfChildren = c.noOfChildren;
00141 }
00142 break;
00143 }
00144 setChild(newNoOfChildren-1, child);
00145 }
00146
00147 }}
00148
00149