XACC
token.h
Go to the documentation of this file.
1 /*
2  * This file is part of Quantum++.
3  *
4  * MIT License
5  *
6  * Copyright (c) 2013 - 2020 Vlad Gheorghiu.
7  *
8  * Permission is hereby granted, free of charge, to any person obtaining a copy
9  * of this software and associated documentation files (the "Software"), to deal
10  * in the Software without restriction, including without limitation the rights
11  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
12  * copies of the Software, and to permit persons to whom the Software is
13  * furnished to do so, subject to the following conditions:
14  *
15  * The above copyright notice and this permission notice shall be included in
16  * all copies or substantial portions of the Software.
17  *
18  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
21  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
22  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
23  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
24  * SOFTWARE.
25  */
26 
32 #ifndef QASM_TOKEN_H_
33 #define QASM_TOKEN_H_
34 
35 namespace qpp {
36 namespace qasm {
37 
42 class Location : public IDisplay {
43  std::string fname_ = "";
44  idx line_ = 1;
45  idx column_ = 1;
46 
47  public:
51  Location() = default;
52 
60  Location(const std::string& fname, idx line, idx column)
61  : fname_(fname), line_(line), column_(column) {}
62 
68  Location(const Location& loc)
69  : fname_(loc.fname_), line_(loc.line_), column_(loc.column_) {}
70 
80  std::ostream& display(std::ostream& os) const {
81  os << fname_ << ":" << line_ << ":" << column_;
82  return os;
83  }
84 
90  const std::string& get_filename() const { return fname_; }
91 
97  idx get_linenum() const { return line_; }
98 
104  idx get_column() const { return column_; }
105 
113  void advance_line(idx num = 1) {
114  line_ += num;
115  column_ = 0;
116  }
117 
123  void advance_column(idx num = 1) { column_ += num; }
124 };
125 
131 class Token : public IDisplay {
132  public:
136  enum class Kind {
137  unknown,
138  eof,
139  comment,
140  identifier,
141  real,
142  nninteger,
143  string,
144  l_square,
145  r_square,
146  l_paren,
147  r_paren,
148  l_brace,
149  r_brace,
150  period,
151  star,
152  plus,
153  minus,
154  arrow,
155  slash,
156  caret,
157  semicolon,
158  equalequal,
159  comma,
160  colon,
161  kw_include,
162  kw_barrier,
163  kw_creg,
164  kw_cx,
165  kw_gate,
166  kw_if,
167  kw_measure,
168  kw_pi,
169  kw_opaque,
170  kw_openqasm,
171  kw_qreg,
172  kw_reset,
173  kw_u,
174  kw_sin,
175  kw_cos,
176  kw_tan,
177  kw_exp,
178  kw_ln,
179  kw_sqrt
180  };
181 
185  Token() = default;
186 
196  Token(Location loc, Kind k, const std::string& value)
197  : loc_(loc), kind_(k), value_(value) {}
198 
204  Kind kind() const { return kind_; }
205 
212  bool is(Kind k) const { return kind_ == k; }
213 
220  bool is_not(Kind k) const { return kind_ != k; }
221 
228  template <typename... Ts>
229  bool is_one_of(Kind k1, Kind k2, Ts... ks) const {
230  return is(k1) || is_one_of(k2, ks...);
231  }
232 
240  operator double() { return std::stof(value_); }
241 
247  operator std::string() { return std::string(value_); }
248 
256  operator idx() { return std::stoi(value_); }
257 
265  operator int() { return std::stoi(value_); }
266 
272  const Location& location() const { return loc_; }
273 
281  friend std::ostream& operator<<(std::ostream& os, const Kind& k) {
282  switch (k) {
283  case Kind::unknown:
284  os << "UNKNOWN";
285  break;
286  case Kind::eof:
287  os << "EOF";
288  break;
289  case Kind::comment:
290  os << "COMMENT";
291  break;
292  case Kind::identifier:
293  os << "ID";
294  break;
295  case Kind::real:
296  os << "REAL";
297  break;
298  case Kind::nninteger:
299  os << "INT";
300  break;
301  case Kind::string:
302  os << "STRING";
303  break;
304  case Kind::l_square:
305  os << "LBRACKET";
306  break;
307  case Kind::r_square:
308  os << "RBRACKET";
309  break;
310  case Kind::l_paren:
311  os << "LPAREN";
312  break;
313  case Kind::r_paren:
314  os << "RPAREN";
315  break;
316  case Kind::l_brace:
317  os << "LBRACE";
318  break;
319  case Kind::r_brace:
320  os << "RBRACE";
321  break;
322  case Kind::period:
323  os << "PERIOD";
324  break;
325  case Kind::star:
326  os << "STAR";
327  break;
328  case Kind::plus:
329  os << "PLUS";
330  break;
331  case Kind::minus:
332  os << "MINUS";
333  break;
334  case Kind::arrow:
335  os << "RARROW";
336  break;
337  case Kind::slash:
338  os << "SLASH";
339  break;
340  case Kind::caret:
341  os << "CARAT";
342  break;
343  case Kind::semicolon:
344  os << "SEMICOLON";
345  break;
346  case Kind::equalequal:
347  os << "EQUALS";
348  break;
349  case Kind::comma:
350  os << "COMMA";
351  break;
352  case Kind::colon:
353  os << "COLON";
354  break;
355  case Kind::kw_include:
356  os << "INCLUDE";
357  break;
358  case Kind::kw_barrier:
359  os << "BARRIER";
360  break;
361  case Kind::kw_creg:
362  os << "CREG";
363  break;
364  case Kind::kw_cx:
365  os << "CX";
366  break;
367  case Kind::kw_gate:
368  os << "GATE";
369  break;
370  case Kind::kw_if:
371  os << "IF";
372  break;
373  case Kind::kw_measure:
374  os << "MEASURE";
375  break;
376  case Kind::kw_pi:
377  os << "PI";
378  break;
379  case Kind::kw_opaque:
380  os << "OPAQUE";
381  break;
382  case Kind::kw_openqasm:
383  os << "OPENQASM";
384  break;
385  case Kind::kw_qreg:
386  os << "QREG";
387  break;
388  case Kind::kw_reset:
389  os << "RESET";
390  break;
391  case Kind::kw_u:
392  os << "UNITARY";
393  break;
394  case Kind::kw_sin:
395  os << "SIN";
396  break;
397  case Kind::kw_cos:
398  os << "COS";
399  break;
400  case Kind::kw_tan:
401  os << "TAN";
402  break;
403  case Kind::kw_exp:
404  os << "EXP";
405  break;
406  case Kind::kw_ln:
407  os << "LN";
408  break;
409  case Kind::kw_sqrt:
410  os << "SQRT";
411  break;
412  }
413  return os;
414  }
415 
424  std::ostream& display(std::ostream& os) const {
425  os << kind_;
426  switch (kind_) {
427  case Kind::identifier:
428  os << "(" << value_ << ")";
429  break;
430  case Kind::real:
431  os << "(" << std::stof(value_) << ")";
432  break;
433  case Kind::nninteger:
434  os << "(" << std::stoi(value_) << ")";
435  break;
436  case Kind::string:
437  os << "(\"" << value_ << "\")";
438  break;
439  default:
440  break;
441  }
442  return os;
443  }
444 
445  private:
446  Location loc_ = Location();
447  Kind kind_ = Kind::unknown;
448  std::string value_ = "";
449 };
450 
454 static const std::unordered_map<std::string, Token::Kind> keywords{
455  {"include", Token::Kind::kw_include},
456  {"barrier", Token::Kind::kw_barrier},
457  {"creg", Token::Kind::kw_creg},
458  {"CX", Token::Kind::kw_cx},
459  {"gate", Token::Kind::kw_gate},
460  {"if", Token::Kind::kw_if},
461  {"measure", Token::Kind::kw_measure},
462  {"pi", Token::Kind::kw_pi},
463  {"opaque", Token::Kind::kw_opaque},
464  {"OPENQASM", Token::Kind::kw_openqasm},
465  {"qreg", Token::Kind::kw_qreg},
466  {"reset", Token::Kind::kw_reset},
467  {"U", Token::Kind::kw_u},
468  {"sin", Token::Kind::kw_sin},
469  {"cos", Token::Kind::kw_cos},
470  {"tan", Token::Kind::kw_tan},
471  {"exp", Token::Kind::kw_exp},
472  {"ln", Token::Kind::kw_ln},
473  {"sqrt", Token::Kind::kw_sqrt}};
474 
475 } /* namespace qasm */
476 } /* namespace qpp */
477 
478 #endif /* QASM_TOKEN_H_ */
Quantum++ main namespace.
Definition: circuits.h:35