fork
Configure Feed
Select the types of activity you want to include in your feed.
this repo has no description
fork
Configure Feed
Select the types of activity you want to include in your feed.
1/* -*- mode: C++; c-basic-offset: 2; indent-tabs-mode: nil -*- */
2/*
3 * Main authors:
4 * Guido Tack <tack@gecode.org>
5 *
6 * Copyright:
7 * Guido Tack, 2006
8 *
9 * This file is part of Gecode, the generic constraint
10 * development environment:
11 * http://www.gecode.org
12 *
13 * Permission is hereby granted, free of charge, to any person obtaining
14 * a copy of this software and associated documentation files (the
15 * "Software"), to deal in the Software without restriction, including
16 * without limitation the rights to use, copy, modify, merge, publish,
17 * distribute, sublicense, and/or sell copies of the Software, and to
18 * permit persons to whom the Software is furnished to do so, subject to
19 * the following conditions:
20 *
21 * The above copyright notice and this permission notice shall be
22 * included in all copies or substantial portions of the Software.
23 *
24 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
25 * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
26 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
27 * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
28 * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
29 * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
30 * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
31 *
32 */
33
34#ifndef GECODE_GIST_SPACENODE_HH
35#define GECODE_GIST_SPACENODE_HH
36
37#include <gecode/gist/node.hh>
38#include <gecode/kernel.hh>
39
40namespace Gecode { namespace Gist {
41
42 /** \brief Status of nodes in the search tree
43 */
44 enum NodeStatus {
45 SOLVED, ///< Node representing a solution
46 FAILED, ///< Node representing failure
47 BRANCH, ///< Node representing a branch
48 UNDETERMINED, ///< Node that has not been explored yet
49 STOP, ///< Node representing stop point
50 UNSTOP, ///< Node representing ignored stop point
51 };
52
53 static const unsigned int FIRSTBIT = 24; //< First free bit in status word
54 static const unsigned int STATUSMASK = 7<<20; //< Mask for accessing status
55 static const unsigned int MAXDISTANCE = (1<<20)-1; //< Maximum representable distance
56 static const unsigned int DISTANCEMASK = (1<<20)-1; //< Mask for accessing distance
57
58 /// %Statistics about the search tree
59 class Statistics : public StatusStatistics {
60 public:
61 /// Number of solutions
62 int solutions;
63 /// Number of failures
64 int failures;
65 /// Number of choice nodes
66 int choices;
67 /// Number of open, undetermined nodes
68 int undetermined;
69 /// Maximum depth of the tree
70 int maxDepth;
71
72 /// Constructor
73 Statistics(void)
74 : solutions(0), failures(0), choices(0), undetermined(1), maxDepth(0) {}
75 };
76
77 class SpaceNode;
78
79 /// \brief Static reference to the currently best space
80 class BestNode {
81 public:
82 /// The currently best node found, or nullptr
83 SpaceNode* s;
84 /// Constructor
85 BestNode(SpaceNode* s0);
86 };
87
88 /// \brief A node of a search tree of %Gecode spaces
89 class SpaceNode : public Node {
90 protected:
91 /** \brief A copy used for recomputation, or nullptr
92 *
93 * If the copy is marked, it is a working copy, i.e.,
94 * it does not have to be kept for recomputation.
95 */
96 Space* copy;
97 protected:
98 const Choice* choice;
99
100 /** \brief Status of the node
101 *
102 * If the node has a working copy, the first 20 bits encode the distance
103 * to the closest copy. The next 5 bits encode the NodeStatus, and the
104 * remaining bits are used by the VisualNode class for further flags.
105 */
106 unsigned int nstatus;
107
108 /// Set distance from copy
109 void setDistance(unsigned int d);
110
111 /// Return distance from copy
112 unsigned int getDistance(void) const;
113
114 /// Set status flag
115 void setFlag(int flag, bool value);
116
117 /// Return status flag
118 bool getFlag(int flag) const;
119
120 /// Flags for SpaceNodes
121 enum SpaceNodeFlags {
122 HASOPENCHILDREN = FIRSTBIT,
123 HASFAILEDCHILDREN,
124 HASSOLVEDCHILDREN
125 };
126 /// Last bit used for SpaceNode flags
127 static const int LASTBIT = HASSOLVEDCHILDREN;
128
129 private:
130 /// Set whether the node has children that are not fully explored
131 void setHasOpenChildren(bool b);
132 /// Set whether the subtree of this node is known to contain failure
133 void setHasFailedChildren(bool b);
134 /// Set whether the subtree of this node is known to contain solutions
135 void setHasSolvedChildren(bool b);
136
137 /// Recompute workingSpace from a copy higher up, return distance to copy
138 int recompute(NodeAllocator& na,
139 BestNode* curBest, int c_d, int a_d);
140
141 /// Book-keeping of open children
142 void closeChild(const NodeAllocator& na,
143 bool hadFailures, bool hadSolutions);
144 protected:
145 /// Set status to \a s
146 void setStatus(NodeStatus s);
147 /// Acquire working space, either from parent or by recomputation
148 void acquireSpace(NodeAllocator& na,
149 BestNode* curBest, int c_d, int a_d);
150 public:
151 /// Construct node with parent \a p
152 SpaceNode(int p);
153 /// Construct root node from Space \a root and branch-and-bound object \a better
154 SpaceNode(Space* root);
155
156 /// Return working space. Receiver must delete the space.
157 Space* getSpace(NodeAllocator& na,
158 BestNode* curBest, int c_d, int a_d);
159
160 /// Return working space (if present).
161 const Space* getWorkingSpace(void) const;
162
163 /// Clear working space and copy (if present and this is not the root).
164 void purge(const NodeAllocator& na);
165
166 /// Free allocated memory
167 void dispose(void);
168
169 /// Return whether this node is the currently best solution
170 bool isCurrentBest(BestNode* curBest);
171
172 /** \brief Compute and return the number of children
173 *
174 * On a node whose status is already determined, this function
175 * just returns the number of children. On an undetermined node,
176 * it first acquires a Space (possibly through recomputation), and
177 * then asks for its status. If the space is solved or failed, the
178 * node's status will be set accordingly, and 0 will be returned.
179 * Otherwise, the status is SS_BRANCH, and as many new children will
180 * be created as the branch has alternatives, and the number returned.
181 */
182 int getNumberOfChildNodes(NodeAllocator& na,
183 BestNode* curBest,
184 Statistics& stats,
185 int c_d, int a_d);
186
187 /// Return current status of the node
188 NodeStatus getStatus(void) const;
189
190 /// Return whether this node still has open children
191 bool isOpen(void);
192 /// Return whether the subtree of this node has any failed children
193 bool hasFailedChildren(void);
194 /// Return whether the subtree of this node has any solved children
195 bool hasSolvedChildren(void);
196 /// Return whether the subtree of this node has any open children
197 bool hasOpenChildren(void);
198 /// Return number of open children
199 int getNoOfOpenChildren(const NodeAllocator& na);
200 /// Set number of open children to \a n
201 void setNoOfOpenChildren(int n);
202 /// Return whether the node has a copy
203 bool hasCopy(void);
204 /// Return whether the node has a working space
205 bool hasWorkingSpace(void);
206
207 /// Return alternative number of this node
208 int getAlternative(const NodeAllocator& na) const;
209 /// Return choice of this node
210 const Choice* getChoice(void);
211 };
212
213}}
214
215#endif
216
217// STATISTICS: gist-any