Token.h 3.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. #ifndef FORTH_KATA_TOKEN_H
  2. #define FORTH_KATA_TOKEN_H
  3. #include <iosfwd>
  4. #include <stdexcept>
  5. #include <string>
  6. #include <gsl/assert>
  7. namespace forth {
  8. namespace token {
  9. /**
  10. * Structure representing a number token (An integer literal).
  11. */
  12. struct Number final
  13. {
  14. int value; ///< The numeric value of the token.
  15. bool operator==(Number const &rhs) const noexcept;
  16. bool operator!=(Number const &rhs) const noexcept;
  17. };
  18. /**
  19. * Overloaded output operator for Number tokens.
  20. * @param os The output stream.
  21. * @param number The number.
  22. * @return The output stream.
  23. */
  24. std::ostream &operator<<(std::ostream &os, Number const &number);
  25. /**
  26. * Structure representing a keyword token (Special words with fixed meaning).
  27. */
  28. struct Keyword final
  29. {
  30. std::string value;
  31. bool operator==(Keyword const &rhs) const noexcept;
  32. bool operator!=(Keyword const &rhs) const noexcept;
  33. };
  34. /**
  35. * Overloaded output operator for Keyword tokens.
  36. * @param os The output stream.
  37. * @param keyword The keyword.
  38. * @return The output stream.
  39. */
  40. std::ostream &operator<<(std::ostream &os, Keyword const &keyword);
  41. /**
  42. * Structure representing a word token (Words that are neither keywords nor numbers).
  43. */
  44. struct Word final
  45. {
  46. std::string value;
  47. bool operator==(Word const &rhs) const noexcept;
  48. bool operator!=(Word const &rhs) const noexcept;
  49. };
  50. /**
  51. * Overloaded output operator for Word tokens.
  52. * @param os The output stream.
  53. * @param word The word.
  54. * @return The output stream.
  55. */
  56. std::ostream &operator<<(std::ostream &os, Word const &word);
  57. } // namespace token
  58. struct WrongTokenException : std::runtime_error
  59. {
  60. using std::runtime_error::runtime_error;
  61. using std::runtime_error::operator=;
  62. };
  63. class Token final
  64. {
  65. enum class Type
  66. {
  67. Number,
  68. Keyword,
  69. Word,
  70. };
  71. public:
  72. Token(token::Number value) noexcept;
  73. Token(token::Keyword value) noexcept;
  74. Token(token::Word value) noexcept;
  75. Token(Token const &src);
  76. Token(Token &&src) noexcept;
  77. Token &operator=(Token const &src);
  78. Token &operator=(Token &&src) noexcept;
  79. ~Token() noexcept;
  80. bool IsNumber() const noexcept;
  81. bool IsKeyword() const noexcept;
  82. bool IsWord() const noexcept;
  83. token::Number const &GetNumber() const;
  84. token::Keyword const &GetKeyword() const;
  85. token::Word const &GetWord() const;
  86. bool operator==(Token const &rhs) const noexcept;
  87. bool operator!=(Token const &rhs) const noexcept;
  88. private:
  89. void destroy() noexcept;
  90. template<typename TType>
  91. void destroy(TType *p)
  92. {
  93. Expects(p != nullptr);
  94. p->~TType();
  95. }
  96. Type type;
  97. union
  98. {
  99. token::Number number;
  100. token::Keyword keyword;
  101. token::Word word;
  102. };
  103. };
  104. /**
  105. * Overloaded output operator for Tokens.
  106. * @param os The output stream.
  107. * @param token The token.
  108. * @return The output stream.
  109. */
  110. std::ostream &operator<<(std::ostream &os, Token const &token);
  111. } // namespace forth
  112. #endif // !FORTH_KATA_TOKEN_H