Scheduler.cpp
Go to the documentation of this file.
1 /*
2  * Scheduler.h
3  * @brief an example how inference can be used for scheduling qualifiers
4  * @date Mar 26, 2011
5  * @author Frank Dellaert
6  */
7 
10 #include <gtsam/base/debug.h>
11 #include <gtsam/base/timing.h>
12 
13 #include <boost/tokenizer.hpp>
14 
15 #include <fstream>
16 #include <iomanip>
17 #include <cmath>
18 
19 namespace gtsam {
20 
21  using namespace std;
22 
23  Scheduler::Scheduler(size_t maxNrStudents, const string& filename):
24  maxNrStudents_(maxNrStudents)
25  {
26  typedef boost::tokenizer<boost::escaped_list_separator<char> > Tokenizer;
27 
28  // open file
29  ifstream is(filename.c_str());
30  if (!is) {
31  cerr << "Scheduler: could not open file " << filename << endl;
32  throw runtime_error("Scheduler: could not open file " + filename);
33  }
34 
35  string line; // buffer
36 
37  // process first line with faculty
38  if (getline(is, line, '\r')) {
39  Tokenizer tok(line);
40  Tokenizer::iterator it = tok.begin();
41  for (++it; it != tok.end(); ++it)
42  addFaculty(*it);
43  }
44 
45  // for all remaining lines
46  size_t count = 0;
47  while (getline(is, line, '\r')) {
48  if (count++ > 100) throw runtime_error("reached 100 lines, exiting");
49  Tokenizer tok(line);
50  Tokenizer::iterator it = tok.begin();
51  addSlot(*it++); // add slot
52  // add availability
53  for (; it != tok.end(); ++it)
54  available_ += (it->empty()) ? "0 " : "1 ";
55  available_ += '\n';
56  }
57  } // constructor
58 
60  void Scheduler::addStudent(const string& studentName,
61  const string& area1, const string& area2,
62  const string& area3, const string& advisor) {
63  assert(nrStudents()<maxNrStudents_);
64  assert(facultyInArea_.count(area1));
65  assert(facultyInArea_.count(area2));
66  assert(facultyInArea_.count(area3));
67  size_t advisorIndex = facultyIndex_[advisor];
68  Student student(nrFaculty(), advisorIndex);
69  student.name_ = studentName;
70  // We fix the ordering by assigning a higher index to the student
71  // and numbering the areas lower
73  student.key_ = DiscreteKey(j, nrTimeSlots());
74  Key base = 3*nrStudents();
75  student.keys_[0] = DiscreteKey(base+0, nrFaculty());
76  student.keys_[1] = DiscreteKey(base+1, nrFaculty());
77  student.keys_[2] = DiscreteKey(base+2, nrFaculty());
78  student.areaName_[0] = area1;
79  student.areaName_[1] = area2;
80  student.areaName_[2] = area3;
81  students_.push_back(student);
82  }
83 
85  const DiscreteKey& Scheduler::key(size_t s, boost::optional<size_t> area) const {
86  return area ? students_[s].keys_[*area] : students_[s].key_;
87  }
88 
89  const string& Scheduler::studentName(size_t i) const {
90  assert(i<nrStudents());
91  return students_[i].name_;
92  }
93 
94  const DiscreteKey& Scheduler::studentKey(size_t i) const {
95  assert(i<nrStudents());
96  return students_[i].key_;
97  }
98 
99  const string& Scheduler::studentArea(size_t i, size_t area) const {
100  assert(i<nrStudents());
101  return students_[i].areaName_[area];
102  }
103 
105  void Scheduler::addStudentSpecificConstraints(size_t i, boost::optional<size_t> slot) {
106  bool debug = ISDEBUG("Scheduler::buildGraph");
107 
108  assert(i<nrStudents());
109  const Student& s = students_[i];
110 
111  if (!slot && !slotsAvailable_.empty()) {
112  if (debug) cout << "Adding availability of slots" << endl;
113  assert(slotsAvailable_.size()==s.key_.second);
115  }
116 
117  // For all areas
118  for (size_t area = 0; area < 3; area++) {
119 
120  DiscreteKey areaKey = s.keys_[area];
121  const string& areaName = s.areaName_[area];
122 
123  if (debug) cout << "Area constraints " << areaName << endl;
124  assert(facultyInArea_[areaName].size()==areaKey.second);
125  CSP::add(areaKey, facultyInArea_[areaName]);
126 
127  if (debug) cout << "Advisor constraint " << areaName << endl;
128  assert(s.advisor_.size()==areaKey.second);
129  CSP::add(areaKey, s.advisor_);
130 
131  if (debug) cout << "Availability of faculty " << areaName << endl;
132  if (slot) {
133  // get all constraints then specialize to slot
134  size_t dummyIndex = maxNrStudents_*3+maxNrStudents_;
135  DiscreteKey dummy(dummyIndex, nrTimeSlots());
136  Potentials::ADT p(dummy & areaKey, available_); // available_ is Doodle string
137  Potentials::ADT q = p.choose(dummyIndex, *slot);
139  CSP::push_back(f);
140  } else {
141  CSP::add(s.key_, areaKey, available_); // available_ is Doodle string
142  }
143  }
144 
145  // add mutex
146  if (debug) cout << "Mutex for faculty" << endl;
147  addAllDiff(s.keys_[0] & s.keys_[1] & s.keys_[2]);
148  }
149 
150 
152  void Scheduler::buildGraph(size_t mutexBound) {
153  bool debug = ISDEBUG("Scheduler::buildGraph");
154 
155  if (debug) cout << "Adding student-specific constraints" << endl;
156  for (size_t i = 0; i < nrStudents(); i++)
158 
159  // special constraint for MN
160  if (studentName(0) == "Michael N") CSP::add(studentKey(0),
161  "0 0 0 0 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1 1");
162 
163  if (!mutexBound) {
164  DiscreteKeys dkeys;
165  for(const Student& s: students_)
166  dkeys.push_back(s.key_);
167  addAllDiff(dkeys);
168  } else {
169  if (debug) cout << "Mutex for Students" << endl;
170  for (size_t i1 = 0; i1 < nrStudents(); i1++) {
171  // if mutexBound=1, we only mutex with next student
172  size_t bound = min((i1 + 1 + mutexBound), nrStudents());
173  for (size_t i2 = i1 + 1; i2 < bound; i2++) {
174  addAllDiff(studentKey(i1), studentKey(i2));
175  }
176  }
177  }
178  } // buildGraph
179 
181  void Scheduler::print(const string& s, const KeyFormatter& formatter) const {
182  cout << s << " Faculty:" << endl;
183  for(const string& name: facultyName_)
184  cout << name << '\n';
185  cout << endl;
186 
187  cout << s << " Slots:\n";
188  size_t i = 0;
189  for(const string& name: slotName_)
190  cout << i++ << " " << name << endl;
191  cout << endl;
192 
193  cout << "Availability:\n" << available_ << '\n';
194 
195  cout << s << " Area constraints:\n";
196  for(const FacultyInArea::value_type& it: facultyInArea_)
197  {
198  cout << setw(12) << it.first << ": ";
199  for(double v: it.second)
200  cout << v << " ";
201  cout << '\n';
202  }
203  cout << endl;
204 
205  cout << s << " Students:\n";
206  for (const Student& student: students_)
207  student.print();
208  cout << endl;
209 
210  CSP::print(s + " Factor graph");
211  cout << endl;
212  } // print
213 
215  void Scheduler::printAssignment(sharedValues assignment) const {
216  // Not intended to be general! Assumes very particular ordering !
217  cout << endl;
218  for (size_t s = 0; s < nrStudents(); s++) {
219  Key j = 3*maxNrStudents_ + s;
220  size_t slot = assignment->at(j);
221  cout << studentName(s) << " slot: " << slotName_[slot] << endl;
222  Key base = 3*s;
223  for (size_t area = 0; area < 3; area++) {
224  size_t faculty = assignment->at(base+area);
225  cout << setw(12) << studentArea(s,area) << ": " << facultyName_[faculty]
226  << endl;
227  }
228  cout << endl;
229  }
230  }
231 
233  void Scheduler::printSpecial(sharedValues assignment) const {
234  Values::const_iterator it = assignment->begin();
235  for (size_t area = 0; area < 3; area++, it++) {
236  size_t f = it->second;
237  cout << setw(12) << studentArea(0,area) << ": " << facultyName_[f] << endl;
238  }
239  cout << endl;
240  }
241 
243  void Scheduler::accumulateStats(sharedValues assignment, vector<
244  size_t>& stats) const {
245  for (size_t s = 0; s < nrStudents(); s++) {
246  Key base = 3*s;
247  for (size_t area = 0; area < 3; area++) {
248  size_t f = assignment->at(base+area);
249  assert(f<stats.size());
250  stats[f]++;
251  } // area
252  } // s
253  }
254 
257  gttic(my_eliminate);
258  // TODO: fix this!!
259  size_t maxKey = keys().size();
260  Ordering defaultKeyOrdering;
261  for (size_t i = 0; i<maxKey; ++i)
262  defaultKeyOrdering += Key(i);
263  DiscreteBayesNet::shared_ptr chordal = this->eliminateSequential(defaultKeyOrdering);
264  gttoc(my_eliminate);
265  return chordal;
266  }
267 
271 
272  if (ISDEBUG("Scheduler::optimalAssignment")) {
273  DiscreteBayesNet::const_iterator it = chordal->end()-1;
274  const Student & student = students_.front();
275  cout << endl;
276  (*it)->print(student.name_);
277  }
278 
279  gttic(my_optimize);
280  sharedValues mpe = chordal->optimize();
281  gttoc(my_optimize);
282  return mpe;
283  }
284 
287  sharedValues best;
288  throw runtime_error("bestSchedule not implemented");
289  return best;
290  }
291 
294  sharedValues bestSchedule) const {
295  sharedValues best;
296  throw runtime_error("bestAssignment not implemented");
297  return best;
298  }
299 
300 } // gtsam
301 
302 
sharedValues optimalAssignment() const
Definition: Scheduler.cpp:269
void add(const DiscreteKey &j, SOURCE table)
Scheduler(size_t maxNrStudents)
Definition: Scheduler.h:72
sharedValues bestSchedule() const
Definition: Scheduler.cpp:286
sharedValues bestAssignment(sharedValues bestSchedule) const
Definition: Scheduler.cpp:293
Global debugging flags.
#define min(a, b)
Definition: datatypes.h:19
std::vector< std::string > facultyName_
Definition: Scheduler.h:53
std::map< std::string, size_t > facultyIndex_
Definition: Scheduler.h:52
ArrayXcf v
Definition: Cwise_arg.cpp:1
std::vector< std::string > slotName_
Definition: Scheduler.h:53
std::vector< DiscreteKey > keys_
Definition: Scheduler.h:29
const std::string & studentName(size_t i) const
Definition: Scheduler.cpp:89
Definition: Half.h:150
size_t nrTimeSlots() const
Definition: Scheduler.h:95
DecisionTree choose(const L &label, size_t index) const
Definition: DecisionTree.h:180
IsDerived< DERIVEDFACTOR > push_back(boost::shared_ptr< DERIVEDFACTOR > factor)
Add a factor directly using a shared_ptr.
Definition: FactorGraph.h:166
double bound(double a, double min, double max)
Definition: PoseRTV.cpp:17
void addStudent(const std::string &studentName, const std::string &area1, const std::string &area2, const std::string &area3, const std::string &advisor)
Definition: Scheduler.cpp:60
size_t nrStudents() const
current number of students
Definition: Scheduler.h:130
Key maxKey(const PROBLEM &problem)
bool stats
const KeyFormatter & formatter
void printAssignment(sharedValues assignment) const
Definition: Scheduler.cpp:215
#define gttic(label)
Definition: timing.h:280
std::vector< double > advisor_
Definition: Scheduler.h:31
void addStudentSpecificConstraints(size_t i, boost::optional< size_t > slot=boost::none)
Definition: Scheduler.cpp:105
#define ISDEBUG(S)
Definition: debug.h:60
std::pair< Key, size_t > DiscreteKey
Definition: DiscreteKey.h:34
std::vector< Student > students_
Definition: Scheduler.h:49
const std::string & studentArea(size_t i, size_t area) const
Definition: Scheduler.cpp:99
FacultyInArea facultyInArea_
Definition: Scheduler.h:57
std::function< std::string(Key)> KeyFormatter
Typedef for a function to format a key, i.e. to convert it to a string.
Definition: Key.h:35
Point2(* f)(const Point3 &, OptionalJacobian< 2, 3 >)
static bool debug
boost::transform_iterator< boost::function1< ConstKeyValuePair, const ConstKeyValuePtrPair & >, KeyValueMap::const_iterator > const_iterator
Const forward iterator, with value type ConstKeyValuePair.
Definition: Values.h:124
RealScalar s
EIGEN_DEVICE_FUNC const Scalar & q
void addSlot(const std::string &slotName)
Definition: Scheduler.h:91
boost::shared_ptr< DiscreteFactor > shared_ptr
shared_ptr to this class
void buildGraph(size_t mutexBound=7)
Definition: Scheduler.cpp:152
traits
Definition: chartTesting.h:28
const DiscreteKey & studentKey(size_t i) const
Definition: Scheduler.cpp:94
FastVector< sharedFactor >::const_iterator const_iterator
Definition: FactorGraph.h:101
void print(const std::string &s="Scheduler", const KeyFormatter &formatter=DefaultKeyFormatter) const override
Definition: Scheduler.cpp:181
#define gttoc(label)
Definition: timing.h:281
void addAllDiff(const DiscreteKey &key1, const DiscreteKey &key2)
Add a binary AllDiff constraint.
Definition: CSP.h:42
std::vector< std::string > areaName_
Definition: Scheduler.h:30
DiscreteBayesNet::shared_ptr eliminate() const
Definition: Scheduler.cpp:256
float * p
size_t nrFaculty() const
Definition: Scheduler.h:82
boost::shared_ptr< BayesNetType > eliminateSequential(OptionalOrderingType orderingType=boost::none, const Eliminate &function=EliminationTraitsType::DefaultEliminate, OptionalVariableIndex variableIndex=boost::none) const
boost::shared_ptr< This > shared_ptr
void print(const std::string &s="DiscreteFactorGraph", const KeyFormatter &formatter=DefaultKeyFormatter) const override
print
Annotation for function names.
Definition: attr.h:36
Annotation indicating that a class derives from another given type.
Definition: attr.h:42
void addFaculty(const std::string &facultyName)
Definition: Scheduler.h:77
const DiscreteKey & key(size_t s, boost::optional< size_t > area=boost::none) const
Definition: Scheduler.cpp:85
std::uint64_t Key
Integer nonlinear key type.
Definition: types.h:61
std::ptrdiff_t j
Timing utilities.
boost::shared_ptr< Values > sharedValues
std::vector< double > slotsAvailable_
Definition: Scheduler.h:63
size_t maxNrStudents_
Definition: Scheduler.h:46
void accumulateStats(sharedValues assignment, std::vector< size_t > &stats) const
Definition: Scheduler.cpp:243
DiscreteKeys is a set of keys that can be assembled using the & operator.
Definition: DiscreteKey.h:37
std::string available_
Definition: Scheduler.h:60
void printSpecial(sharedValues assignment) const
Definition: Scheduler.cpp:233


gtsam
Author(s):
autogenerated on Sat May 8 2021 02:43:54