编译原理 TEST语言,词法分析+语法分析(C/C++语言)

临时写了个语法分析的代码,可以顺便输出语法树,以后有时间慢慢解释具体结构吧~

代码:

#include<bits/stdc++.h>
#define xcx(x) printf("ojbk %d\n",(x))
using namespace std;
const int KEY_WORD_NUM = 13 ;
const int OPERATOR_WORD_NUM = 19;
const int DELIMITER_WORD_NUM = 6 ;
const int row_limit = 130;

//词法分析常量
const string _data_type = "data type" ;
const string _statement_keyword = "statement keyword" ;
const string _identifier = "identifier" ;
const string _single_arithmetic_operator = "single arithmetic operator" ;
const string _compare_operator = "compare operator" ;
const string _double_arithmetic_operator = "double arithmetic operator" ;
const string _delimiter = "delimiter" ;
const string _unsigned_number = "unsigned number" ;
const string _const_string  = "const string" ;
const string _const_character = "const character";
const string ANNOTATIONL1 = "//" ;
const string ANNOTATIONL2 = "/*" ;
const string key_word [ KEY_WORD_NUM ] = { "break", "if", "else", "for", "while", "do", "int", "double", "char", "read", "write", "bool", "string" } ;
const string operator_word [ OPERATOR_WORD_NUM ]= { "+=", "-=", "*=", "\=", "+", "-", "*", "/", "=", "++", "--", "<", ">", "<=", ">=", "!=", "==", "//", "/*" } ;
const string delimiter_word [ DELIMITER_WORD_NUM ] = { "(", ")", "{", "}", ",", ";"};

//语法分析常量
const string _program = "program" ;
const string _declaration = "declaration" ;
const string _expression = "expression" ;
const string _expression_bool = "expression bool" ;
const string _expression_cal = "expression cal" ;
const string _term = "term" ;
const string _factor = "factor" ;
const string _statement = "statement" ;
const string _statement_if = "if - statement";
const string _statement_while = "while - statement" ;
const string _statement_do_while = "do-while - statement";
const string _statement_for = "for - statement" ;
const string _statement_write = "write - statement" ;
const string _statement_read = "read - statement" ;
const string _statement_compound = "compound statement" ;
const string _statement_expression = "expression statement" ;
const string _constant = "constant" ;
const string _number = "number" ;
struct Node_operator {
    string str;
    bool is_terminator;
    map < char, int > next;
    Node_operator(){
        str.clear();
        is_terminator = false;
        next.clear();
    }
    Node_operator( const string &str ){
        this -> next.clear();
        this -> str = str;
        this -> is_terminator = false;
    }
};
struct Word {
    string type;
    string val;
    Word(){
        type.clear();
        val.clear();
    }
    Word( const string &str , const string &val ){
        this -> type = str;
        this -> val = val;
    }
    void print(){
        printf( " %s  %s\n", this -> type.c_str(), this -> val.c_str() );
    }
    bool operator != (const Word &other) const {
        return other.type != this->type || other.val != this->val ;
    }
    bool operator == (const Word &other) const {
        return other.type == this->type && other.val == this->val ;
    }
};
struct Unit {
    vector< Unit > u ;
    string val ;
    string type;
    bool is_error;
    Unit(){
        is_error = false ;
    }
    Unit ( const string type ) {
        this -> is_error = false ;
        this -> type = type;
    }
    Unit ( const Word &w ) {
        this -> is_error = false ;
        this -> type = w.type ;
        this -> val = w.val ;
        u.clear();
    }
    inline void print() {
        printf( " %s ( %s ) " , val.c_str() , type.c_str() ) ;
    }
    inline void println() {
        print();
        printf("\n");
    }
    void push( const Unit &ut ) {
        this -> val += ut.val;
        this -> u.push_back( ut ) ;
    }
    void push( const Word &w ) {
        this -> val += w.val;
        this -> u.push_back( Unit(w) ) ;
    }
    void clear() {
        this -> val.clear();
        this -> u.clear();
    }
};
struct Node {
    Unit x ;
    int deep , vl , vr , mid , tl , tr , fa , id;
    bool is_level , is_enough_v , is_enough_t ;
    Node () {};
    Node ( Unit u , int deep , int fa ) {
        this -> deep = deep ;
        this -> x = u;
        if ( u.u.size() == 0 ) this -> is_level = true;
        else this -> is_level = false ;
        this -> fa = fa ;
        this -> x.type = "[" + u.type + "]";
    }
    int TypeLength() {
        return x.type.length();
    }
    int ValLength() {
        return x.val.length();
    }
};
int now_line = 1 , error_type = 0;
char ch = 0;
FILE *fp ;
map < string, int > key_word_id;
map < char, int > operator_word_head;
vector < Node_operator > state_graph;
vector < Word > ans ;
string error_information , fin_name , fout_name ;
Word finish , error_word, wd;
Unit error_unit;
char tree_map[300][row_limit+5];


void read(char &c){
    if( fscanf( fp , "%c" , &c ) == EOF ) c = EOF;
    if( c == '\n' ) now_line++ ;
}

///词法分析识别函数
inline bool Is_Character ( const char &c ) {
    return c>='A'&&c<='Z' || c>='a'&&c<='z' || c=='_';
}
inline bool Is_Number( const char &c ) {
    return c>='0'&&c<='9' ;
}
inline bool Is_Operator_head ( const char &c ) {
    return operator_word_head.count(c) > 0 ;
}
inline bool Is_Data_type ( const string &s ){
    return s=="int" || s=="double" || s=="char" || s=="string" || s=="bool" ;
}
inline bool Is_Blank ( const char &c ) {
    return c == ' ' || c == '\t' || c == '\n' ;
}
inline bool Is_Delimiter ( const char &c ) {
    return c=='(' || c==')' || c=='{' || c=='}' || c==';' || c==',' ;
}
inline bool Is_Compare_operator ( const string &s ) {
    return s=="<" || s==">" || s=="<=" || s==">=" || s=="==" || s=="!=" ;
}

void InitTestScan(){
//读取标识符
    key_word_id.clear();
    for( int i=0; i<KEY_WORD_NUM; i++ ) {
        key_word_id[ key_word[i] ] = i;
    }
//读取运算符头字母
    operator_word_head.clear();
    for( int i=0; i<OPERATOR_WORD_NUM; i++ ) {
        operator_word_head[ operator_word[i][0] ] = i;
    }
//运算符建图
    state_graph.clear();
    state_graph.push_back( Node_operator() );
    for( int i=0; i<OPERATOR_WORD_NUM; i++ ) {
        const string &temp = operator_word[i];
        int node_index = 0;
        for( int j=0; j<(int)temp.length(); j++ ) {
            Node_operator &now_node = state_graph[node_index];
            if( now_node.next.count( temp[j] ) == 0 ) {
                now_node.next[ temp[j] ] = state_graph.size();
                state_graph.push_back( Node_operator( now_node.str +temp[j] ) );
                node_index = state_graph.size() -1 ;
            }
            else{
                node_index = now_node.next[ temp[j] ];
            }
        }
        state_graph[node_index].is_terminator = true ;
    }
//vector<> 清空
    ans.clear();
//当前行起点为1
    now_line = 1;
//常量终止Word赋值
    finish.type.clear();    finish.val.clear();
//error处理信息
    error_type = 0 ;
    error_information.clear() ;
    error_word = Word( string("error"), string("?") );
    error_unit.is_error =true; error_unit.type.clear(); error_unit.val.clear();
}
void PrintError( int op );
int InputTestScan(){
    printf( "input the name of the source program...\n" );
    cin >> fin_name ;
    fp = fopen( fin_name.c_str(), "r" );
    if( fp == NULL ) return 1;
    //else fclose( fp );
    //printf( "input the name of the output file...\n" );
    //cin >> fout_name ;
    //freopen( fin_name.c_str(), "r", stdin ) ;
    return 0;
}
void InitGetWord(){
    InitTestScan();
    read( ch );
}

///语法分析识别函数
Word GetWord(){ //读取一个标识
    Word ret = finish ;
    while( ch != EOF ){
        while( Is_Blank(ch) ){
            read( ch );
            if( ch == EOF ) return ret;
        }
        if( Is_Character(ch) == true ) { //处理标识符
            string str;
            while( Is_Character(ch) == true || Is_Number(ch) == true ) {
                str += ch;
                read( ch );
            }
            if( key_word_id.count(str) > 0 ) {
                if( Is_Data_type( str ) == true ) {
                    ret = Word(_data_type, str);
                }
                else {
                    ret = Word(_statement_keyword, str);
                }
            }
            else {
                ret = Word(_identifier, str) ;
            }
        }
        else if( Is_Number(ch) == true ) { //处理数字常量
            string str;
            bool is_decimal = false;
            while( Is_Number(ch) == true ) {
                str +=ch;
                read( ch );
            }
            if( ch == '.' ) {
                is_decimal = true;
                str +=ch;
                read( ch );
                while( Is_Number(ch) == true ) {
                    str +=ch;
                    read( ch );
                }
                if( Is_Character(ch) || ch == '.' ){
                    error_type = 3;
                    while( !Is_Blank(ch) && !Is_Delimiter(ch) ) {
                        str += ch;
                        read( ch );
                    }
                    if ( ch == '\n' ) now_line-- ;
                    error_information = str;
                    return error_word;
                }
            }
            if( is_decimal == true ) {
                if( str.back() == '.' ) {
                    error_information = str ;
                    error_type = 4;
                    return error_word;
                }
            }
            ret = Word( _unsigned_number, str ) ;
        }
        else if ( ch == '\'' ) { //处理单引号
            string str;
            str +=ch;
            read( ch );
            while( ch!='\'' && ch!='\n' ) {
                if( ch == '\\' ) {
                    str +=ch;
                    read( ch );
                }
                str +=ch;
                read( ch );
            }
            if( ch != '\'' ) {
                error_type = 5;
                error_information = str;
                return error_word;
            }
            str +=ch;
            ret = Word(_const_character, str) ;
            read( ch );
            if( ret.val.length() > 3 && ret.val[1] !='\\' ) {
                error_type = 6;
                error_information = str;
                return error_word;
            }
        }
        else if ( ch == '"' ) { //处理双引号
            string str;
            str +=ch;
            read( ch );
            while( ch!='"' && ch!='\n' ) {
                if( ch == '\\' ) {
                    str +=ch;
                    read( ch );
                }
                str +=ch;
                read( ch );
            }
            if( ch != '"' ) {
                error_type = 7;
                error_information = str;
                return error_word;
            }
            str +=ch;
            ret = Word( _const_string, str ) ;
            read( ch );
        }
        else if ( Is_Operator_head(ch) == true ) { //处理运算符
            string str ;
            int node_index = 0;
            while( state_graph[node_index].next.count(ch) > 0 ) {
                node_index = state_graph[node_index].next[ch] ;
                read( ch );
                while( Is_Blank(ch) == true ) read( ch ) ;
            }
            Node_operator &now_node = state_graph[node_index];
            if( now_node.str == ANNOTATIONL1 ) { //处理注释1
                while( ch != '\n' ) read( ch );
                read( ch );
            }
            else if( now_node.str == ANNOTATIONL2 ) { //处理注释2
                char pre_ch = ch;
                read( ch );
                while( !(pre_ch == '*' && ch == '/') ) {
                    pre_ch = ch;
                    read( ch );
                }
                read( ch );
            }
            else if( state_graph[node_index].is_terminator == false ) { //运算符不合法
                error_information = state_graph[node_index].str ;
                error_type = 8 ;
                return error_word;
            }
            else { //合法运算符
                str = now_node.str;
                if( str == "++" || str == "--" ) {
                    ret = Word( _single_arithmetic_operator , str) ;
                }
                else if( Is_Compare_operator(str) == true ) {
                    ret = Word( _compare_operator , str) ;
                }
                else {
                    ret = Word( _double_arithmetic_operator , str ) ;
                }
            }
        }
        else if( Is_Delimiter(ch) == true ) { //处理分界符
            string str ;
            str = ch;
            read( ch ) ;
            ret = Word (_delimiter , str );
        }
        else{ //不合法字符
            error_information = ch;
            while( Is_Blank(ch) == false ) {
                error_information += ch ;
                read( ch );
            }
            error_type = 9;
            return error_word;
        }
        if( error_type != 0 || ( ret.type.length() != 0 || ret.val.length() != 0 ) ) return ret;
    }
}

Unit GetProgram() ;
Unit GetDeclaration() ;
Unit GetExpression() ;
Unit GetExpressionBool() ;
Unit GetExpressionCal() ;
Unit GetTerm() ;
Unit GetFactor() ;
Unit GetStatement() ;
Unit GetStatementIf() ;
Unit GetStatementWhile() ;
Unit GetStatementDoWhile() ;
Unit GetStatementFor() ;
Unit GetStatementWrite() ;
Unit GetStatementRead() ;
Unit GetStatementCompound() ;
Unit GetStatementExpression() ;
Unit GetConstant() ;
Unit GetNumber() ;

void PrintTree ( Unit &root ) ; // 想不想看看怎么秀操作
vector < Node > Bfs( Unit &s );

void test(){
    fin_name = "in.txt" ;
    fp = fopen( fin_name.c_str(), "r" );
    InitGetWord();
    Unit ans = GetProgram();
    PrintError( error_type );
    PrintTree ( ans );
    /*while( ch != EOF ){
        ans.push_back( GetWord() );
        ans[ans.size()-1].print();
        if( error_type != 0 ) {
            printf("error!");
            //PrintError( error_type );
            error_type = 0;
            error_information.clear();
        }
    }*/
}
int TestScan(){
    //int ret = InputTestScan();
    //if( ret != 0 ) return ret;
    InitGetWord();
    while( ch != EOF ){
        ans.push_back( GetWord() );
        if( error_type != 0 ) {
            //PrintError( error_type );
            error_type = 0;
            error_information.clear();
        }
    }
    return 0;
}
void OutPut(){
    freopen( fout_name.c_str(), "w", stdout );
    for( int i=0; i<ans.size(); i++ ) {
        ans[i].print();
    }
    /*printf( "----------------------------------------------------------------\n" );*/
}

int main()
{
    test(); return 0;
    int flag = TestScan();
    if( flag == 0 ) {
        OutPut();
        freopen( "CON", "w", stdout );
        printf( "\nLexical analysis completed, the results have been saved in the \"%s\" file !\n", fout_name.c_str() );
    }
    else {
        freopen( "CON", "w", stdout );
    }
    return 0;
}

Unit GetProgram() {
    Unit ret = Unit( _program ) , add ;
    wd = GetWord();
    if ( wd == error_word ) return error_unit;
    while( wd != finish ) {
        if( wd.type == _data_type ) { // 声明语句
            add = GetDeclaration();
        }
        else { // 语句
            add = GetStatement() ;
        }
        if ( add.is_error == true ) {
            return error_unit ;
        }
        else {
            ret.push ( add ) ;
        }
    }
    return ret;
}
Unit GetDeclaration() {
    Unit ret = Unit( _declaration ) , add ;
    ret.push ( wd ) ;
    wd = GetWord();
    if ( wd == error_word ) return error_unit ;
    if ( wd.type != _identifier ) { // <标识符>
        error_type = 10 ;
        error_information = ret.val ;
        return error_unit ;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord();
        if ( wd == error_word ) return error_unit ;
    }

    if ( wd.val == "=" ) { // = <表达式>
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
        add = GetExpression();
        if( add.is_error == true ){
            return error_unit ;
        }
        else {
            ret.push ( add ) ;
        }
    }
    while( wd.val == "," ) { // 循环添加 , <标识符>
        ret.push ( wd ) ;
        wd = GetWord();
        if ( wd == error_word ) return error_unit ;
        if ( wd.type != _identifier ) {
            error_type = 10 ;
            error_information = "," ;
            return error_unit ;
        }
        else {
            ret.push ( wd ) ;
            wd = GetWord();
            if ( wd == error_word ) return error_unit ;
        }
        if( wd.val == "=" ) {
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
            add = GetExpression();
            if( add.is_error == true ){
                return error_unit;
            }
            else {
                ret.push ( add ) ;
            }
        }
    }
    if( wd.val != ";" ){ // 处理分号
        error_type = 11 ;
        error_information = ret.val ;
        return error_unit;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    return ret;
}
Unit GetExpression() {
    Unit ret = Unit ( _expression ) , add ;
    if ( wd.type != _identifier ) { // bool表达式
        add = GetExpressionBool();
        if ( add.is_error == true ) {
            return error_unit ;
        }
        else {
            ret.push ( add ) ;
        }
    }
    else{
        long fileadd = ftell( fp ) ; // 记录当前位置
        char rem_ch = ch ; // 记录当前ch
        Word rem_wd = wd; // 记录当前wd
        int rem_now_line = now_line ; // 记录当前行数
        //printf("rem: %c",ch); wd.print();

        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
        if ( wd.val == "=" || wd.val == "+=" || wd.val == "-=" || wd.val == "\=" || wd.val == "*=" ) { // 赋值表达式
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
            add = GetExpressionBool();
            if ( add.is_error == true ){
                return error_unit;
            }
            else{
                ret.push ( add ) ;
            }
        }
        else { //bool 表达式
            fseek( fp , fileadd , 0 );// 返回记录文件位置
            ch = rem_ch ;
            wd = rem_wd;
            ret.clear();
            now_line = rem_now_line ;
            //printf("back : %c",ch); wd.print();

            add = GetExpressionBool();
            if ( add.is_error == true ) {
                return error_unit ;
            }
            else {
                ret.push ( add ) ;
            }
        }
    }
    return ret;
}
Unit GetExpressionBool() {
    Unit ret = Unit ( _expression_bool ) , add ;
    add = GetExpressionCal() ;
    if ( add.is_error == true ) {
        return error_unit;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.type == _compare_operator ){
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
        add = GetExpressionCal() ;
        if ( add.is_error == true ) {
            return error_unit;
        }
        else {
            ret.push ( add ) ;
        }
    }
    return ret;
}
Unit GetExpressionCal() {
    Unit ret = Unit ( _expression_cal ) , add ;
    add = GetTerm() ;
    if ( add.is_error == true ) {
        return error_unit;
    }
    else {
        ret.push ( add ) ;
        if ( wd.val == "+" || wd.val == "-" ) {
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
            add = GetTerm() ;
            if ( add.is_error == true ) {
                return error_unit;
            }
            else {
                ret.push ( add ) ;
            }
        }
    }

    return ret;
}
Unit GetTerm() {
    Unit ret = Unit( _term ) , add ;
    add = GetFactor() ;
    if ( add.is_error == true ) {
        return error_unit ;
    }
    else {
        ret.push ( add ) ;
        if ( wd.val == "*" || wd.val == "/" ) {
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
            add = GetTerm() ;
            if ( add.is_error == true ) {
                return error_unit;
            }
            else {
                ret.push ( add ) ;
            }
        }
    }
    return ret;
}
Unit GetFactor() {
    Unit ret = Unit ( _factor ) , add ;
    if ( wd.val == "(" ) { //表达式
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
        add = GetExpression() ;
        if ( add.is_error == true ) {
            ret.is_error = true ;
            return ret;
        }
        else {
            ret.push( add ) ;
        }
        if ( wd.val != ")" ) {
            error_type = 13 ;
            error_information = ret.val;
            ret.is_error = true ;
            return ret;
        }
        else {
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
        }
    }
    else if ( wd.type == _identifier ) { //标识符
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
        if ( wd.type == _single_arithmetic_operator ) { // 自运算
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
        }
    }
    else if ( wd.val == "-" || wd.type == _unsigned_number ) { //数字常量
        if( wd.type == _unsigned_number ) {
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
        }
        else {
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
            if ( wd.type == _unsigned_number ) {
                ret.push ( wd ) ;
                wd = GetWord() ;
                if ( wd == error_word ) return error_unit ;
            }
            else {
                error_type = 13 ;
                error_information = ret.val ;
                ret.is_error = true ;
                return ret;
            }
        }
    }
    else if ( wd.type == _const_character || wd.type == _const_string ) { //字符或字符串常量
        ret.push ( wd ) ;
        wd = GetWord();
        if ( wd == error_word ) return error_unit ;
    }
    else { //不合法factor
        error_type = 13 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    return ret;
}
Unit GetStatement() {
    Unit ret = Unit( _statement ) , add ;
    if ( wd.type == _statement_keyword ) {
        if( wd.val == "if" ) { // if-statement
            add = GetStatementIf() ;
        }
        else if( wd.val == "while" ) { // while-statement
            add = GetStatementWhile() ;
        }
        else if( wd.val == "do" ) { // do_while-statement
            add = GetStatementDoWhile() ;
        }
        else if( wd.val == "for" ) { // for-statement
            add = GetStatementFor() ;
        }
        else if( wd.val == "write" ) { // write-statement
            add = GetStatementWrite() ;
        }
        else if( wd.val == "read" ) { // read-statement
            add = GetStatementRead() ;
        }
        else { // break 语句
            ret.push ( wd ) ;
            wd = GetWord() ;
            if ( wd == error_word ) return error_unit ;
            if ( wd.val != ";" ) {
                error_type = 11 ;
                error_information = ret.val ;
                return error_unit ;
            }
            else {
                ret.push ( wd ) ;
                wd = GetWord();
                if ( wd == error_word ) return error_unit ;
            }
            return ret;
        }
    }
    else {
         if( wd.val == "{" ) { //复合语句
            add = GetStatementCompound() ;
        }
        else { //表达式语句
            add = GetStatementExpression() ;
        }
    }
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( add ) ;
    }
    return ret;
}
Unit GetStatementIf() {
    Unit ret = Unit( _statement_if ) , add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    if ( wd.val != "(" ) {
        error_type = 15 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetExpression() ;
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != ")" ) {
        error_type = 13 ;
        error_information = add.val ;
        ret.is_error = true;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetStatement();
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val == "else" ) { //else 语句
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
        add = GetStatement() ;
        if ( add.is_error == true ) {
            ret.is_error = true ;
            return ret;
        }
        else {
            ret.push ( add ) ;
        }
    }
    return ret;
}
Unit GetStatementWhile() {
    Unit ret = Unit( _statement_while ) , add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    if ( wd.val != "(" ) {
        error_type = 13 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetExpression() ;
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != ")" ) {
        error_type = 15 ;
        error_information = add.val ;
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetStatement() ;
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( add ) ;
    }
    return ret;
}
Unit GetStatementDoWhile() {
    Unit ret = Unit( _statement_do_while ) , add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    add = GetStatement() ;
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != "while" ) {
        error_type = 18 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    if( wd.val != "(" ) { // 左括号
        error_type = 15;
        error_information = ret.val;
        return error_unit ;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit;
    }
    add = GetExpressionBool() ;
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( add ) ;
    }
    if( wd.val != ")" ) { // 右括号
        error_type = 13;
        error_information = ret.val;
        return error_unit ;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit;
    }
    if ( wd.val != ";" ) {
        error_type = 11 ;
        error_information = add.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    return ret;
}
Unit GetStatementFor() {
    Unit ret = Unit( _statement_for ), add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    if ( wd.val != "(" ) {
        error_type = 15 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetExpression() ; // 表达式一
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != ";" ) { // 分号一
        error_type = 11;
        error_information = add.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetExpression() ; // 表达式二
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != ";" ) { //分号二
        error_type = 11;
        error_information = add.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetExpression() ; // 表达式三
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != ")" ) { // 右括号
        error_type = 13 ;
        error_information = add.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetStatement() ; // 循环语句
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( add ) ;
    }
    return ret ;
}
Unit GetStatementWrite() {
    Unit ret = Unit( _statement_write ) , add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    if ( wd.val != "(" ) {
        error_type = 15 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    add = GetExpressionCal() ;//算术表达式
    if ( add.is_error == true ) {
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( add ) ;
    }
    if ( wd.val != ")" ) {
        error_type = 13 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    if ( wd.val != ";" ) {
        error_type = 11 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    return ret;
}
Unit GetStatementRead() {
    Unit ret = Unit( _statement_read ) , add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    if ( wd.val != "(" ) {
        error_type = 15 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret ;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    if ( wd.type != _identifier ) {
        error_type = 17 ;
        error_information = wd.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    if ( wd.val != ")" ) {
        error_type = 13 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    if ( wd.val != ";" ) {
        error_type = 11 ;
        error_information = ret.val ;
        ret.is_error = true ;
        return ret;
    }
    else {
        ret.push ( wd ) ;
        wd = GetWord() ;
        if ( wd == error_word ) return error_unit ;
    }
    return ret;
}
Unit GetStatementCompound() {
    Unit ret = Unit( _statement_compound ), add ;
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    while( wd.val != "}" ) {
        add = GetStatement();
        if ( add.is_error == true ) {
            ret.is_error = true ;
            return ret;
        }
        else {
            ret.push ( add ) ;
        }
    }
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    return ret ;
}
Unit GetStatementExpression() {
    Unit ret = Unit( _statement_expression ) , add ;
    while( wd.val != ";" ) {
        add = GetExpression();
        if ( add.is_error == true ) {
            ret.is_error = true ;
            return ret;
        }
        else {
            ret.push ( add ) ;
        }
    }
    ret.push ( wd ) ;
    wd = GetWord() ;
    if ( wd == error_word ) return error_unit ;
    return ret;
}



void PrintError( int op ){
///文件操作相关
    if( op == 1 ) { //输入文件打开失败
        printf( "return = %d  ERROR: fail to open the source program !\n" , op );
    }
    if( op == 2 ) { //输出文件不存在, 理论不可能发生
        printf( "return = %d  ERROR: fail to open the output file !\n" , op );
    }
///词法分析相关
    if( op == 3 ) { //数字常量不合法
        printf( "return = %d  ERROR: %s is not a number in line %d !\n" , op , error_information.c_str() , now_line );
    }
    if( op == 4 ) { //小数点后缺少数字
        printf( "return = %d  ERROR: Missing Numbers behind the decimal point in line %d !\n" , op , now_line );
    }
    if( op == 5 ) { //单引号不匹配
        printf( "return = %d  ERROR: missing terminating \' behind %s character in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 6 ) { // 字符常量超长
        printf( "return = %d  ERROR: Character constants %s are excessively long in line %d !\n", error_information.c_str() , now_line );
    }
    if( op == 7 ) { //双引号不匹配
        printf( "return = %d  ERROR: missing terminating \" behind %s character in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 8 ) { //运算符不合法
        printf( "return = %d  ERROR: the operator %s is not valid in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 9 ) { //非合法字符
        printf( "return = %d  ERROR: %s was not legal character in line %d !\n", op , error_information.c_str() , now_line );
    }

///语法分析相关
    if( op == 10 ) { //缺少标识符
        printf( "return = %d  ERROR: miss declaration after %s in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 11 ) { //缺少分号
        printf( "return = %d  ERROR: miss ';' after %s in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 12 ) { //不是合法表达式
        printf( "return = %d  ERROR: %s is not a expression in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 13 ) { //缺少右括号
        printf( "return = %d  ERROR: miss ')' after %s in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 14 ) { //不是因子
        printf( "return = %d  ERROR: %s is not a factor in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 15 ) { //缺少左括号
        printf( "return = %d  ERROR: miss '(' before %s in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 16 ) { //write括号中信息不合法
        printf( "return = %d  ERROR: %s is not a declaration in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 17 ) { //read括号中信息不合法
        printf( "return = %d  ERROR: %s is not a expression in line %d !\n", op , error_information.c_str() , now_line );
    }
    if( op == 18 ) { //缺少while
        printf( "return = %d  ERROR: miss while after 'do' in line %d !\n", op , now_line );
    }
}
vector < Node > Bfs( Unit &s ) {
    queue < Node > q ;
    vector < Node > ret ;
    q.push( Node( s , 0 , -1 ) ) ;
    while( !q.empty() ) {
        Node now = q.front() ;
        ret.push_back( now ) ;
        q.pop();
        for ( int i=0; i<now.x.u.size(); i++ ) {
            q.push ( Node( now.x.u[i] , now.deep+1 , ret.size()-1 ) ) ;
        }
    }
    /*for ( int i=0; i<ret.size(); i++ ) {
        printf("%d ",ret[i].deep);
        ret[i].x.println();
    }*/
    return ret;
}
void draw( int row_num = 100 ) {
    for ( int i=0; i<row_num; i++ ) {
        for ( int j=0; j<row_limit; j++ ) {
            if ( tree_map[i][j] != 0 )
                printf( "%c" , tree_map[i][j] ) ;
            else {
                printf(" ");
            }
        }
        printf("\n");
    }
}
void PrintTree ( Unit &root ) {
    ///build tree sequence
    vector < Node > temp = Bfs ( root );
    vector < Node > e_vector ;
    vector< vector < Node > > a ;
    for ( int i=0; i<temp.size(); i++ ) {
        temp[i].id = i;
        if ( temp[i].deep >= a.size() ) {
            a.push_back( e_vector );
        }
        a[ temp[i].deep ].push_back( temp[i] ) ;
    }
    for ( int i=0; i<a.size(); i++ ){
        int len = row_limit / a[i].size();
        int limit = len - 2;
        for( int j=0; j<a[i].size(); j++ ) {
            Node &now = a[i][j] ;
            now.mid = j*len + len/2 ;
            if ( now.TypeLength() > limit ) {
                now.tl = j*len +1;
                now.tr = now.tl + limit -1 ;
                now.is_enough_t = false ;
            }
            else {
                now.tl = now.mid - now.TypeLength()/2 ;
                now.tr = now.tl + now.TypeLength() - 1 ;
                now.is_enough_t = true ;
            }
            if ( now.ValLength() > limit ) {
                now.vl = j*len +1;
                now.vr = now.vl + limit -1 ;
                now.is_enough_v = false ;
            }
            else {
                now.vl = now.mid - now.ValLength()/2 ;
                now.vr = now.vl + now.ValLength() - 1 ;
                now.is_enough_v = true ;
            }
        }
    }
    for ( int i=0; i<a.size(); i++ ) {
        for ( int j=0; j<a[i].size(); j++ ) {
            temp[ a[i][j].id ] = a[i][j];
            //printf("%d %d %d \n",i,a[i][j].id ,temp[a[i][j].id].mid);
        }
    }
    ///paint tree map
    memset ( tree_map, 0, sizeof(tree_map) ) ;
    int line_pos = 0 , pre_l = row_limit , pre_r = -1 ;
    for( int i=0; i<a.size(); i++ ) {
        if ( i!=0 ) {
            for ( int j=0; j<a[i].size(); j++ ) {// 划横线
                if ( j==0 || a[i][j].fa!=a[i][j-1].fa ) {
                    pre_l = min( a[i][j].mid , temp[a[i][j].fa].mid ) ;
                }
                if ( j==a[i].size()-1 || a[i][j].fa!=a[i][j+1].fa ) {
                    pre_r = max( a[i][j].mid , temp[a[i][j].fa].mid ) ;
                //printf("%d %d \n",pre_l,pre_r);
                    for ( int k=pre_l; k<=pre_r; k++ ) {
                        tree_map [ line_pos ] [ k ] = '-' ;
                    }
                }
            }
            line_pos++ ;
            for ( int j=0; j<a[i].size(); j++ ) { // 划竖线
                tree_map [ line_pos ] [ a[i][j].mid ] = '|';
            }
            line_pos++ ;
        }
        for ( int j=0; j<a[i].size(); j++ ) {// 输出 Val
            Node &now = a[i][j] ;
            if ( now.is_enough_v == false ) {
                for ( int k=now.vl, p=0; k<=now.vr; k++, p++ ) {
                    tree_map[line_pos][k] = now.x.val[p] ;
                }
                for ( int k=now.vr+1; k<=now.vr+3; k++ ) {
                    tree_map[line_pos][k] = '.' ;
                }
            }
            else {
                for ( int k=now.vl, p=0 ; p<now.x.val.length(); k++, p++ ) {
                    tree_map[line_pos][k] = now.x.val[p] ;
                }
            }
        }
        line_pos++ ;
        for ( int j=0; j<a[i].size(); j++ ) {// 输出 Type
            Node &now = a[i][j] ;
            if ( now.is_enough_t == false ) {
                for ( int k=now.tl, p=0; k<=now.tr; k++, p++ ) {
                    tree_map[line_pos][k] = now.x.type[p] ;
                }
                for ( int k=now.tr+1; k<=now.tr+3; k++ ) {
                    tree_map[line_pos][k] = '.' ;
                }
            }
            else {
                for ( int k=now.tl, p=0 ; p<now.x.type.length(); k++, p++ ) {
                    tree_map[line_pos][k] = now.x.type[p] ;
                }
            }
        }
        line_pos++ ;
        for ( int j=0; j<a[i].size(); j++ ) { // 划竖线(后)
            if ( a[i][j].is_level == false )
                tree_map [ line_pos ] [ a[i][j].mid ] = '|';
        }
        line_pos++ ;

    }
    draw ( line_pos ) ;
}


测试数据

//合法输入:
//www*= a++;
k += c++ -2*x*-3.4;
/*
write(-3.2*(i-3)*(j-4));
int a , b , c = 12 , d = "sadas" ;
*/
/*
while(t--){
    if(3==5-2) write(-3.0*x*y+w*2);
}
*/

/*k = c++ ;

write(-3*i*(j-4));
9.0.0.2.

double c = -6.2;
for( i=-2 ; i<=w ; i++ ) {
    for( j = 3.8; j<i ;j ++) {
        read(d);
        write(-3*i*(j-4));
    }
}

c++;
b = a++;
int a , b , c = 12 , d = "sadas" ;
int a;
b = a++;

if( c == d ) {
    c = w;
}
while( w-- != k*2.2 );
while ( T-- < = 2 ) {
    t=t+1;
}

read(w);
write(432);
write("sds");
write(4/sd+sd*4);
do{
    i++;
    if(k!=2) break;
}while(23+3==s);
*/

运行截图:

                                                         k+=c++-2*x*-3.4;
                                                             [program]
                                                                 |
                                                                 -
                                                                 |
                                                         k+=c++-2*x*-3.4;
                                                            [statement]
                                                                 |
                                                                 -
                                                                 |
                                                         k+=c++-2*x*-3.4;
                                                      [expression statement]
                                                                 |
                                ------------------------------------------------------------------
                                |                                                                |
                         k+=c++-2*x*-3.4                                                         ;
                          [expression]                                                      [delimiter]
                                |
                     ---------------------------------------------------------------------------------------
                     |                                          |                                          |
                     k                                         +=                                    c++-2*x*-3.4
               [identifier]                       [double arithmetic operator]                     [expression bool]
                                                                                                           |
                                                                 -------------------------------------------
                                                                 |
                                                           c++-2*x*-3.4
                                                         [expression cal]
                                                                 |
                     ---------------------------------------------------------------------------------------
                     |                                          |                                          |
                    c++                                         -                                      2*x*-3.4
                  [term]                          [double arithmetic operator]                          [term]
                     |                                                                                     |
                ------                          -----------------------------------------------------------------
                |                               |                               |                               |
               c++                              2                               *                            x*-3.4
            [factor]                        [factor]              [double arithmetic operator]               [term]
                |                               |                                                               |
          ----------------------                -----                    -------------------------------------------
          |                    |                    |                    |                    |                    |
          c                   ++                    2                    x                    *                  -3.4
    [identifier]      [single arithmetic ...[unsigned number]        [factor]        [double arithmetic ...     [term]
                                                                         |                                         |
                                ------------------------------------------                       -------------------
                                |                                                                |
                                x                                                              -3.4
                          [identifier]                                                       [factor]
                                                                                                 |
                                ------------------------------------------------------------------
                                |                                                                |
                                -                                                               3.4
                  [double arithmetic operator]                                           [unsigned number]


发布了227 篇原创文章 · 获赞 142 · 访问量 9万+

猜你喜欢

转载自blog.csdn.net/qq_36306833/article/details/89893817