Skip to content

Latest commit

 

History

History
209 lines (169 loc) · 10.8 KB

README.md

File metadata and controls

209 lines (169 loc) · 10.8 KB

LiteCompiler_C++

文件结构

├── LiteCompiler_C++                整个项目文件夹
│   ├── .idea                       CLion配置文件
│   ├── CMakeLists.txt              CMake配置文件
│   ├── main.cpp                    主函数
│   ├── src                         存放所有头文件和源文件
│   │   ├── debug                   调试文件
│   │   │   ├── debug.cpp           debug类相关成员函数及变量定义
│   │   │   └── debug.h             debug类声明文件
│   │   ├── error                   错误处理
│   │   │   ├── error.cpp           错误处理函数定义
│   │   │   └── error.h             错误处理函数声明
│   │   ├── FileHandler             文件处理【主要为对文件进行输入输出】
│   │   │   ├── FileHandler.cpp     文件处理类相关成员函数及变量定义
│   │   │   └── FileHandler.h       文件处理类声明
│   │   ├── LexicalAnalysis         词法分析器【语法分析程序的子程序,其结果(Token序列)直接作为语法分析程序的输入】
│   │   │   ├── Lexer.cpp           词法分析器类相关成员函数及变量定义
│   │   │   └── Lexer.h             词法分析器类声明
│   │   ├── Parser                  语法分析器【语法分析程序的主要部分】
│   │   │   ├── Parser.cpp          语法分析器类相关成员函数及变量定义
│   │   │   └── Parser.h            语法分析器类声明
│   │   └── Token                   Token相关文件
│   │       ├── Token.cpp           KEYWORD定义、Token类相关成员函数及变量定义
│   │       └── Token.h             TokenType枚举类型声明、Token类声明、产生式非终结符声明
│   ├── Pictures                    README.md文件中可能用到的图片文件
│   └── VisioSourceDocuments        Visio绘图源文件
└── README.md                       项目介绍【本文件】

构建方法🛠️

构建平台:linux或window10及以上

所需工具:g++(支持c++17及以上),cmake(大于3.28版本)

步骤:在robin文件夹下运行以下命令

mkdir build && cd build && cmake .. && make                          #linux平台
mkdir build; cd build; cmake -G "MinGW Makefiles" ..; mingw32-make   #windows平台

词法分析器

这里列出的关键字和符号主要用于描述编程语言中的词法单元(Lexical Units)或标记(Tokens),在语法解析和编译过程中具有特定的意义。下面是对这些关键字和符号的简要介绍:

  1. 关键字(Keywords)

    • KEYWORD_AND: and表示逻辑与操作,通常用于布尔表达式中。
    • KEYWORD_BREAK: break,用于跳出循环或switch语句。
    • KEYWORD_CHAR: char,字符类型关键字。
    • KEYWORD_CLASS: class,表示定义类的关键字。
    • KEYWORD_CONTINUE: continue,继续下一次循环的关键字。
    • KEYWORD_DO: do,循环语句关键字。
    • KEYWORD_DOUBLE: double,浮点数类型关键字。
    • KEYWORD_ELSE: else,条件语句中的否定分支关键字。
    • KEYWORD_EOF: EOFeof,表示输入结束的关键字。
    • KEYWORD_FALSE: false,布尔类型的假值关键字。
    • KEYWORD_FOR: for,循环语句中的关键字。
    • KEYWORD_FUNCTION: function,定义函数的关键字。
    • KEYWORD_IF: if,条件语句中的条件判断关键字。
    • KEYWORD_INTEGER: integer,整数类型关键字。
    • KEYWORD_NIL: nil,空值关键字,表示空对象或未定义的值。
    • KEYWORD_NOT: not表示逻辑非操作。
    • KEYWORD_NULL: null,空指针。
    • KEYWORD_OR: or表示逻辑或操作。
    • KEYWORD_PRINT: print,输出语句的关键字。
    • KEYWORD_READ: read,读操作关键字。
    • KEYWORD_REPEAT: repeat,循环关键字。
    • KEYWORD_RETURN: return,函数返回语句的关键字。
    • KEYWORD_STRING: string,字符串类型关键字。
    • KEYWORD_SUPER: super,表示父类的关键字。
    • KEYWORD_THIS: this,表示当前对象或实例的关键字。
    • KEYWORD_TRUE: true,布尔类型的真值关键字。
    • KEYWORD_UNTIL: until,循环关键字。
    • KEYWORD_VAR: var,定义变量的关键字。
    • KEYWORD_WHILE: while,循环语句中的关键字。
    • KEYWORD_WRITE: write,写操作关键字。
  2. 符号(Symbols)

    • ASSIGNMENT: =赋值运算符。
    • PLUS: +,加号。
    • PLUS_ASSIGNMENT: +=,赋值加号。
    • MINUS: -,减号。
    • MINUS_ASSIGNMENT: -=,赋值减号。
    • MULTIPLY: *,乘号。
    • MULTIPLY_ASSIGNMENT: *=,赋值乘号。
    • DIVIDE: /,除号。
    • DIVIDE_ASSIGNMENT: /=,赋值除号。
    • AND: &,按位与运算符。
    • AND_ASSIGNMENT: &=,按位与赋值运算符。
    • LOGICAL_AND: &&,逻辑与运算符。
    • OR: |,按位或运算符。
    • OR_ASSIGNMENT: |=,按位或赋值运算符。
    • LOGICAL_OR: ||,逻辑或运算符。
    • XOR: ^,按位异或运算符。
    • XOR_ASSIGNMENT: ^=,按位异或赋值运算符。
    • NOT: ~,按位取反运算符。
    • LOGICAL_NOT: !,逻辑非运算符。
    • NOT_EQUAL: !=,不等于运算符。
    • EQUAL: ==,等于运算符。
    • ABOVE: >,大于运算符。
    • BELOW: <,小于运算符。
    • ABOVE_OR_EUQAL: >=,大于或等于运算符。
    • BELOW_OR_EUQAL: <=,小于或等于运算符。
    • LEFT_PAREN: (,左括号。
    • RIGHT_PAREN: ),右括号。
    • LEFT_BRACKET: [,左方括号。
    • RIGHT_BRACKET: ],右方括号。
    • LEFT_BRACE: {,左花括号。
    • RIGHT_BRACE: },右花括号。
    • D_MARKS: ",双引号。
    • S_MARKS: ',单引号。
    • MEMBER: .,成员访问符。
    • MEMBER_PTR: ->,成员指针访问符。
    • COMMA: ,,逗号。
  3. 其他(Else)

    • IDENTIFIER: 标识符字面量,用于表示变量名、函数名等。
    • INTEGER, FLOAT: 整数和浮点数类型变量。
    • STRING: 字符串类型变量。
    • EMPTY: 空标记。
    • INVALID: 非法的标记,表示词法错误。
    • EOF: 表示已经到达代码文件的末尾。

这些关键字和符号是编程语言中常见的词法单元,通过它们可以构建出语法结构,并进行语法分析、编译和执行代码。

词法分析器完整算法结构图:

graph LR
    Lexer::LexicalAnalyze["Lexer::LexicalAnalyze"] --> |"调用"|Lexer::skipWhitespace["Lexer::skipWhitespace"]
    Lexer::skipWhitespace --> |"跳过当前连续的空格、换行、制表符"|start["当前Token的第一个字符"]
    
    start --> |"英文字母或下划线"| Lexer::parseIdentifier["Lexer::parseIdentifier"]
    start --> |"数字"| Lexer::parseNumber["Lexer::parseNumber"]
    start --> |"其他符号"| Lexer::parseSymbol["Lexer::parseSymbol"]
    
    Lexer::parseIdentifier --> |"扫描直至出现非英文字母或下划线的字符出现时"|IdentifierEnd["End_of_ID_Token"]
    IdentifierEnd --> |"true == Lexer::checkKeyword"|returnKeywordType["相应的关键字"]
    IdentifierEnd --> |"false == Lexer::checkKeyword"|returnIdentifier["Identifier(id)"]
    
    Lexer::parseNumber --> |"扫描直至出现非数字或小数点的字符出现时;或第二次出现小数点时"|NumberEnd["End_of_NUM_Token"]
    NumberEnd --> |"不存在小数点'.'"|NUM_INT["NUM_INT"]
    NumberEnd --> |"存在1个小数点'.'"|NUM_REAL["NUM_REAL"]
    
    
    Lexer::parseSymbol --> |"匹配到 点'.'"|MatchedPoint["MatchedPoint"]
    MatchedPoint --> |"点'.'后面是数字"| NUM_REAL["NUM_REAL"]
    MatchedPoint --> |"点'.'后面不是数字"| Point_Operators["成员访问运算符"]
    
    Lexer::parseSymbol --> |"匹配到正常运算符"| Symbol_Operators["各类运算符"]
    
    Lexer::parseSymbol --> |"匹配到 单引号 OR 双引号"| StringStart["字符串识别"]
    StringStart --> |"匹配到 对应的 单引号 OR 双引号 闭合"| StringEnd["字符串"]
    StringStart --> |"直至换行仍未匹配到 对应的 单引号 OR 双引号 闭合"| StringError["Error:字符串换行"]
    
    Lexer::parseSymbol --> |"匹配到 '/'"| MatchedSlash["MatchedSlash"]
    MatchedSlash --> |"'*' != peekNext() && '/' != peekNext() && '=' != peekNext()"| Divide_Operators["除法运算符"]
    MatchedSlash --> |"'=' == peekNext()"| Divide_Assignmnt_Operators["除法赋值运算符"]
    MatchedSlash --> |"'*' == peekNext()"| CommentBlock["注释块"]
    MatchedSlash --> |"'/' == peekNext()"| Comment["单行注释"]
    CommentBlock --> |"直至文件末尾仍未匹配到 '*/' 闭合"| CompleteError["注释未闭合"]
    CommentBlock --> |"匹配到 '*/' 闭合"| CompleteComment["完成注释过滤"]
    
    
    Lexer::parseSymbol --> |"匹配到 '#'"| Comment["单行注释"]
    Comment --> |"忽略本行"| CompleteComment["完成注释过滤"]
    
    
    
    
    Lexer::parseSymbol --> |"其他无法识别的符号"| Unexpected_character["Unexpected character"]
    
    StringError --> LexicalError["LexicalError"]
    Unexpected_character --> LexicalError["LexicalError"]
    CompleteError --> LexicalError["LexicalError"]
    
    returnKeywordType --> CompleteToken["识别完成一个Token"]
    returnIdentifier --> CompleteToken["识别完成一个Token"]
    NUM_REAL --> CompleteToken["识别完成一个Token"]
    NUM_INT --> CompleteToken["识别完成一个Token"]
    Symbol_Operators --> CompleteToken["识别完成一个Token"]
    StringEnd --> CompleteToken["识别完成一个Token"]
    Point_Operators --> CompleteToken["识别完成一个Token"]
    Divide_Operators --> CompleteToken["识别完成一个Token"]
    Divide_Assignmnt_Operators --> CompleteToken["识别完成一个Token"]
    
    CompleteToken --> NextToken["准备下一个Token的识别"]
    CompleteComment --> NextToken["准备下一个Token的识别"]
    LexicalError --> NextToken["准备下一个Token的识别"]
    
    NextToken --> |"回到跳过空白符号函数,并循环执行此过程直至文件末尾"|Lexer::skipWhitespace["Lexer::skipWhitespace"]
Loading

词法分析器完整算法流程图彩色版:

编译系统设计实践_实验1_算法流程图