-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathLexer.h
More file actions
107 lines (90 loc) · 2.35 KB
/
Lexer.h
File metadata and controls
107 lines (90 loc) · 2.35 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
//
// Created by User on 7/10/2024.
//
#ifndef LEXER_H
#define LEXER_H
#include <algorithm>
#include <iostream>
#include <string>
#include <utility>
enum TokenType {
NUMBER,
PLUS, MINUS, STAR, SLASH,
LPAREN, RPAREN,
LBRACE, RBRACE,
IDENTIFIER,
DEF,
ASSIGN,
COMMA,
SEMICOLON,
END
};
struct Token {
TokenType type;
std::string value;
};
class Lexer {
public:
explicit Lexer(std::string input) : input(std::move(input)), position(0) {}
Token getNextToken();
private:
std::string input;
size_t position;
[[nodiscard]] char currentChar() const {
return position < input.size() ? input[position] : '\0';
}
void advance() {
position++;
}
void skipWhitespace() {
while (std::isspace(currentChar())) {
advance();
}
}
Token number();
Token identifier();
};
inline Token Lexer::number() {
size_t start = position;
while (std::isdigit(currentChar())) {
advance();
}
return { NUMBER, input.substr(start, position - start) };
}
inline Token Lexer::identifier() {
size_t start = position;
while (std::isalnum(currentChar()) || currentChar() == '_') {
advance();
}
return { IDENTIFIER, input.substr(start, position - start) };
}
inline Token Lexer::getNextToken() {
skipWhitespace();
char current = currentChar();
if (std::isdigit(current)) {
return number();
}
if (std::isalpha(current)) {
const std::string text = identifier().value;
if (text == "def") {
return { DEF, text };
}
return { IDENTIFIER, text };
}
switch (current) {
case '+': advance(); return { PLUS, "+" };
case '-': advance(); return { MINUS, "-" };
case '*': advance(); return { STAR, "*" };
case '/': advance(); return { SLASH, "/" };
case '(': advance(); return { LPAREN, "(" };
case ')': advance(); return { RPAREN, ")" };
case '=': advance(); return { ASSIGN, "=" };
case ',': advance(); return { COMMA, "," };
case ';': advance(); return { SEMICOLON, ";" };
case '{': advance(); return { LBRACE, "{" };
case '}': advance(); return { RBRACE, "}" };
case '\0': return { END, "" };
default: throw std::runtime_error("Unexpected character");
}
}
#endif //LEXER_H