Generated on Tue Oct 22 2013 00:48:59 for Gecode by doxygen 1.8.4
ast.hh
Go to the documentation of this file.
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, 2007
8  *
9  * Last modified:
10  * $Date: 2013-05-09 01:32:37 +0200 (Thu, 09 May 2013) $ by $Author: tack $
11  * $Revision: 13625 $
12  *
13  * This file is part of Gecode, the generic constraint
14  * development environment:
15  * http://www.gecode.org
16  *
17  * Permission is hereby granted, free of charge, to any person obtaining
18  * a copy of this software and associated documentation files (the
19  * "Software"), to deal in the Software without restriction, including
20  * without limitation the rights to use, copy, modify, merge, publish,
21  * distribute, sublicense, and/or sell copies of the Software, and to
22  * permit persons to whom the Software is furnished to do so, subject to
23  * the following conditions:
24  *
25  * The above copyright notice and this permission notice shall be
26  * included in all copies or substantial portions of the Software.
27  *
28  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
29  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
30  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
31  * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
32  * LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
33  * OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
34  * WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
35  *
36  */
37 
38 #ifndef __GECODE_FLATZINC_AST_HH__
39 #define __GECODE_FLATZINC_AST_HH__
40 
41 #include <vector>
42 #include <string>
43 #include <iostream>
44 #include <cstdlib>
45 
51 namespace Gecode { namespace FlatZinc { namespace AST {
52 
53  class Call;
54  class Array;
55  class Atom;
56  class SetLit;
57 
60  private:
61  std::string _what;
62  public:
63  TypeError() : _what("") {}
64  TypeError(std::string what) : _what(what) {}
65  std::string what(void) const { return _what; }
66  };
67 
72  public:
74  virtual ~Node(void);
75 
77  void append(Node* n);
78 
80  bool hasAtom(const std::string& id);
82  bool isInt(int& i);
84  bool isFloat(double& i);
86  bool isCall(const std::string& id);
88  Call* getCall(void);
90  bool hasCall(const std::string& id);
92  Call* getCall(const std::string& id);
94  Array* getArray(void);
96  Atom* getAtom(void);
98  std::string getVarName(void);
100  int getIntVar(void);
102  int getBoolVar(void);
104  int getFloatVar(void);
106  int getSetVar(void);
107 
109  int getInt(void);
111  bool getBool(void);
113  double getFloat(void);
115  SetLit *getSet(void);
116 
118  std::string getString(void);
119 
121  bool isIntVar(void);
123  bool isBoolVar(void);
125  bool isSetVar(void);
127  bool isFloatVar(void);
129  bool isInt(void);
131  bool isFloat(void);
133  bool isBool(void);
135  bool isString(void);
137  bool isArray(void);
139  bool isSet(void);
141  bool isAtom(void);
142 
144  virtual void print(std::ostream&) = 0;
145  };
146 
149  public:
150  bool b;
151  BoolLit(bool b0) : b(b0) {}
152  virtual void print(std::ostream& os) {
153  os << "b(" << (b ? "true" : "false") << ")";
154  }
155  };
158  public:
159  int i;
160  IntLit(int i0) : i(i0) {}
161  virtual void print(std::ostream& os) {
162  os << "i("<<i<<")";
163  }
164  };
167  public:
168  double d;
169  FloatLit(double d0) : d(d0) {}
170  virtual void print(std::ostream& os) {
171  os << "f("<<d<<")";
172  }
173  };
176  public:
177  bool interval;
178  int min; int max;
179  std::vector<int> s;
180  SetLit(void) {}
181  SetLit(int min0, int max0) : interval(true), min(min0), max(max0) {}
182  SetLit(const std::vector<int>& s0) : interval(false), s(s0) {}
183  bool empty(void) const {
184  return ( (interval && min>max) || (!interval && s.size() == 0));
185  }
186  virtual void print(std::ostream& os) {
187  os << "s()";
188  }
189  };
190 
192  class GECODE_VTABLE_EXPORT Var : public Node {
193  public:
194  int i; //< Index
195  std::string n; //< Name
197  Var(int i0, const std::string& n0) : i(i0), n(n0) {}
198  };
201  public:
203  BoolVar(int i0, const std::string& n0="") : Var(i0,n0) {}
204  virtual void print(std::ostream& os) {
205  os << "xb("<<i<<")";
206  }
207  };
209  class GECODE_VTABLE_EXPORT IntVar : public Var {
210  public:
211  IntVar(int i0, const std::string& n0="") : Var(i0,n0) {}
212  virtual void print(std::ostream& os) {
213  os << "xi("<<i<<")";
214  }
215  };
218  public:
219  FloatVar(int i0, const std::string& n0="") : Var(i0,n0) {}
220  virtual void print(std::ostream& os) {
221  os << "xf("<<i<<")";
222  }
223  };
225  class GECODE_VTABLE_EXPORT SetVar : public Var {
226  public:
227  SetVar(int i0, const std::string& n0="") : Var(i0,n0) {}
228  virtual void print(std::ostream& os) {
229  os << "xs("<<i<<")";
230  }
231  };
232 
234  class GECODE_VTABLE_EXPORT Array : public Node {
235  public:
236  std::vector<Node*> a;
237  Array(const std::vector<Node*>& a0)
238  : a(a0) {}
240  : a(1) { a[0] = n; }
241  Array(int n=0) : a(n) {}
242  virtual void print(std::ostream& os) {
243  os << "[";
244  for (unsigned int i=0; i<a.size(); i++) {
245  a[i]->print(os);
246  if (i<a.size()-1)
247  os << ", ";
248  }
249  os << "]";
250  }
251  ~Array(void) {
252  for (int i=a.size(); i--;)
253  delete a[i];
254  }
255  };
256 
258  class GECODE_VTABLE_EXPORT Call : public Node {
259  public:
260  std::string id;
262  Call(const std::string& id0, Node* args0)
263  : id(id0), args(args0) {}
264  ~Call(void) { delete args; }
265  virtual void print(std::ostream& os) {
266  os << id << "("; args->print(os); os << ")";
267  }
268  Array* getArgs(unsigned int n) {
269  Array *a = args->getArray();
270  if (a->a.size() != n)
271  throw TypeError("arity mismatch");
272  return a;
273  }
274  };
275 
278  public:
279  Node* a;
281  ArrayAccess(Node* a0, Node* idx0)
282  : a(a0), idx(idx0) {}
283  ~ArrayAccess(void) { delete a; delete idx; }
284  virtual void print(std::ostream& os) {
285  a->print(os);
286  os << "[";
287  idx->print(os);
288  os << "]";
289  }
290  };
291 
293  class GECODE_VTABLE_EXPORT Atom : public Node {
294  public:
295  std::string id;
296  Atom(const std::string& id0) : id(id0) {}
297  virtual void print(std::ostream& os) {
298  os << id;
299  }
300  };
301 
304  public:
305  std::string s;
306  String(const std::string& s0) : s(s0) {}
307  virtual void print(std::ostream& os) {
308  os << "s(\"" << s << "\")";
309  }
310  };
311 
312  inline
313  Node::~Node(void) {}
314 
315  inline void
316  Node::append(Node* newNode) {
317  Array* a = dynamic_cast<Array*>(this);
318  if (!a)
319  throw TypeError("array expected");
320  a->a.push_back(newNode);
321  }
322 
323  inline bool
324  Node::hasAtom(const std::string& id) {
325  if (Array* a = dynamic_cast<Array*>(this)) {
326  for (int i=a->a.size(); i--;)
327  if (Atom* at = dynamic_cast<Atom*>(a->a[i]))
328  if (at->id == id)
329  return true;
330  } else if (Atom* a = dynamic_cast<Atom*>(this)) {
331  return a->id == id;
332  }
333  return false;
334  }
335 
336  inline bool
337  Node::isCall(const std::string& id) {
338  if (Call* a = dynamic_cast<Call*>(this)) {
339  if (a->id == id)
340  return true;
341  }
342  return false;
343  }
344 
345  inline Call*
347  if (Call* a = dynamic_cast<Call*>(this))
348  return a;
349  throw TypeError("call expected");
350  }
351 
352  inline bool
353  Node::hasCall(const std::string& id) {
354  if (Array* a = dynamic_cast<Array*>(this)) {
355  for (int i=a->a.size(); i--;)
356  if (Call* at = dynamic_cast<Call*>(a->a[i]))
357  if (at->id == id) {
358  return true;
359  }
360  } else if (Call* a = dynamic_cast<Call*>(this)) {
361  return a->id == id;
362  }
363  return false;
364  }
365 
366  inline bool
367  Node::isInt(int& i) {
368  if (IntLit* il = dynamic_cast<IntLit*>(this)) {
369  i = il->i;
370  return true;
371  }
372  return false;
373  }
374 
375  inline bool
376  Node::isFloat(double& d) {
377  if (FloatLit* fl = dynamic_cast<FloatLit*>(this)) {
378  d = fl->d;
379  return true;
380  }
381  return false;
382  }
383 
384  inline Call*
385  Node::getCall(const std::string& id) {
386  if (Array* a = dynamic_cast<Array*>(this)) {
387  for (int i=a->a.size(); i--;)
388  if (Call* at = dynamic_cast<Call*>(a->a[i]))
389  if (at->id == id)
390  return at;
391  } else if (Call* a = dynamic_cast<Call*>(this)) {
392  if (a->id == id)
393  return a;
394  }
395  throw TypeError("call expected");
396  }
397 
398  inline Array*
400  if (Array* a = dynamic_cast<Array*>(this))
401  return a;
402  throw TypeError("array expected");
403  }
404 
405  inline Atom*
407  if (Atom* a = dynamic_cast<Atom*>(this))
408  return a;
409  throw TypeError("atom expected");
410  }
411 
412  inline std::string
414  if (Var* a = dynamic_cast<Var*>(this))
415  return a->n;
416  throw TypeError("variable expected");
417  }
418  inline int
420  if (IntVar* a = dynamic_cast<IntVar*>(this))
421  return a->i;
422  throw TypeError("integer variable expected");
423  }
424  inline int
426  if (BoolVar* a = dynamic_cast<BoolVar*>(this))
427  return a->i;
428  throw TypeError("bool variable expected");
429  }
430  inline int
432  if (FloatVar* a = dynamic_cast<FloatVar*>(this))
433  return a->i;
434  throw TypeError("integer variable expected");
435  }
436  inline int
438  if (SetVar* a = dynamic_cast<SetVar*>(this))
439  return a->i;
440  throw TypeError("set variable expected");
441  }
442  inline int
443  Node::getInt(void) {
444  if (IntLit* a = dynamic_cast<IntLit*>(this))
445  return a->i;
446  throw TypeError("integer literal expected");
447  }
448  inline bool
450  if (BoolLit* a = dynamic_cast<BoolLit*>(this))
451  return a->b;
452  throw TypeError("bool literal expected");
453  }
454  inline double
456  if (FloatLit* a = dynamic_cast<FloatLit*>(this))
457  return a->d;
458  throw TypeError("float literal expected");
459  }
460  inline SetLit*
461  Node::getSet(void) {
462  if (SetLit* a = dynamic_cast<SetLit*>(this))
463  return a;
464  throw TypeError("set literal expected");
465  }
466  inline std::string
468  if (String* a = dynamic_cast<String*>(this))
469  return a->s;
470  throw TypeError("string literal expected");
471  }
472  inline bool
474  return (dynamic_cast<IntVar*>(this) != NULL);
475  }
476  inline bool
478  return (dynamic_cast<BoolVar*>(this) != NULL);
479  }
480  inline bool
482  return (dynamic_cast<SetVar*>(this) != NULL);
483  }
484  inline bool
486  return (dynamic_cast<FloatVar*>(this) != NULL);
487  }
488  inline bool
489  Node::isInt(void) {
490  return (dynamic_cast<IntLit*>(this) != NULL);
491  }
492  inline bool
493  Node::isBool(void) {
494  return (dynamic_cast<BoolLit*>(this) != NULL);
495  }
496  inline bool
498  return (dynamic_cast<FloatLit*>(this) != NULL);
499  }
500  inline bool
501  Node::isSet(void) {
502  return (dynamic_cast<SetLit*>(this) != NULL);
503  }
504  inline bool
506  return (dynamic_cast<String*>(this) != NULL);
507  }
508  inline bool
510  return (dynamic_cast<Array*>(this) != NULL);
511  }
512  inline bool
513  Node::isAtom(void) {
514  return (dynamic_cast<Atom*>(this) != NULL);
515  }
516 
517  inline Node*
519  if (Array* a = dynamic_cast<Array*>(n)) {
520  if (a->a.size() == 1) {
521  Node *ret = a->a[0];
522  a->a[0] = NULL;
523  delete a;
524  return ret;
525  }
526  }
527  return n;
528  }
529 
530 }}}
531 
532 #endif
533 
534 // STATISTICS: flatzinc-any