Browse Source

优化了try except和do...while

SongZihuan 5 years ago
parent
commit
c27609d261
3 changed files with 140 additions and 43 deletions
  1. 1 0
      README.md
  2. 50 15
      inter/interpreter.c
  3. 89 28
      paser/syntax.c

+ 1 - 0
README.md

@@ -76,5 +76,6 @@ return x n  函数返回值x,返回n层
 * Div和Log运算检查数字类型
 * 调整了运算优先级,修改了无法读取``5 ** -2``而可以读取``5 ** (-2)``的bug
 * while和for循环新增else语句
+* try...except增加了else和finally语句,并且允许``except``,``except as``,``else``,``finally``为可选语句
 ## 关于GWARF
 最后更新时间 : 2020年05月07日 广州

+ 50 - 15
inter/interpreter.c

@@ -1195,15 +1195,7 @@ GWARF_result for_func(statement *the_statement, var_list *the_var, inter *global
         // after do
         if(the_statement->code.for_cycle.after != NULL){
             GWARF_result tmp_result = traverse(the_statement->code.for_cycle.after, the_var, false, global_inter);
-            if(is_error(&tmp_result)){  // Name Error错误
-                // puts("STOP:: Name No Found!");
-                value = tmp_result;
-                goto return_value;
-            }
-            else if(is_space(&tmp_result)){
-                value = tmp_result;
-                goto return_value;
-            }
+            error_space(tmp_result, return_value, value);
         }
         // continue操作
         if((value.u == cycle_continue) || (value.u == code_continued)){
@@ -1218,6 +1210,7 @@ GWARF_result for_func(statement *the_statement, var_list *the_var, inter *global
             }
             else{
                 value.value.value.int_value -= 1;
+                do_else = false;
                 break;
             }
         }
@@ -1235,9 +1228,14 @@ GWARF_result for_func(statement *the_statement, var_list *the_var, inter *global
             }
             else{
                 value.value.value.int_value -= 1;
+                do_else = false;
                 break;
             }
         }
+
+        if(value.u == rego){  // rewent认为是正常执行
+            do_else = false;
+        }
     }
     if(do_else){
         GWARF_result tmp_result = traverse(the_statement->code.for_cycle.else_do, the_var, false, global_inter);
@@ -1310,7 +1308,7 @@ GWARF_result raise_func(statement *the_statement, var_list *the_var, bool not_cl
 // -----------------try func
 GWARF_result try_func(statement *the_statement, var_list *the_var, inter *global_inter){  // read the statement list with case to run by func
     GWARF_result value = GWARF_result_reset;
-
+    bool do_else = true;
     hash_var *tmp = make_hash_var();  // base_var
     the_var = append_var_list(tmp, the_var);  // run func
 
@@ -1322,12 +1320,14 @@ GWARF_result try_func(statement *the_statement, var_list *the_var, inter *global
     // restart操作[和continue效果相同]
 
     if(is_error(&value)){  // 遇到错误->执行except语句[不需要再检查break...]
+        do_else = false;
         assignment_statement(the_statement->code.try_code.var, the_var, the_var, value,global_inter);
         puts("----except----");
         value = traverse(the_statement->code.try_code.except, the_var, false, global_inter);
         puts("----stop except----");
     }
 
+    // 不使用else
     if(value.u == code_restarted){
         if(value.value.type != INT_value){
             value.value.type = INT_value;
@@ -1344,7 +1344,7 @@ GWARF_result try_func(statement *the_statement, var_list *the_var, inter *global
     }
     
     // continued操作
-    if(value.u == code_continued){
+    else if(value.u == code_continued){
         if(value.value.type != INT_value){
             value.value.type = INT_value;
             value.value.value.int_value = 0;
@@ -1360,7 +1360,7 @@ GWARF_result try_func(statement *the_statement, var_list *the_var, inter *global
     }
 
     // broken操作
-    if(value.u == code_broken){
+    else if(value.u == code_broken){
         if(value.value.type != INT_value){
             value.value.type = INT_value;
             value.value.value.int_value = 0;
@@ -1372,6 +1372,19 @@ GWARF_result try_func(statement *the_statement, var_list *the_var, inter *global
             value.value.value.int_value -= 1;
         }
     }
+
+    if(do_else){  // 不会捕捉break等
+        GWARF_result tmp_result = traverse(the_statement->code.try_code.else_do, the_var, false, global_inter);
+        error_space(tmp_result, return_value, value);   
+    }
+    return_value: 
+    // 执行finally[必须会执行]
+    {
+        GWARF_result tmp_result = traverse(the_statement->code.try_code.finally_do, the_var, false, global_inter);
+        error_space(tmp_result, to_finally, value);   
+    }
+
+    to_finally:
     the_var = free_var_list(the_var);  // free the new var
     return value;
 }
@@ -1492,6 +1505,7 @@ GWARF_result forin_func(statement *the_statement, var_list *the_var, inter *glob
             }
             else{
                 value.value.value.int_value -= 1;
+                do_else = false;
                 break;
             }
         }
@@ -1508,9 +1522,14 @@ GWARF_result forin_func(statement *the_statement, var_list *the_var, inter *glob
             }
             else{
                 value.value.value.int_value -= 1;
+                do_else = false;
                 break;
             }
         }
+
+        if(value.u == rego){  // rewent认为是正常执行
+            do_else = false;
+        }
     }
     if(do_else){
         GWARF_result tmp_result = traverse(the_statement->code.for_in_cycle.else_do, the_var, false, global_inter);
@@ -1578,6 +1597,7 @@ GWARF_result while_func(statement *the_statement, var_list *the_var, inter *glob
             }
             else{
                 value.value.value.int_value -= 1;
+                do_else = false;
                 break;
             }
         }
@@ -1594,9 +1614,14 @@ GWARF_result while_func(statement *the_statement, var_list *the_var, inter *glob
             }
             else{
                 value.value.value.int_value -= 1;
+                do_else = false;
                 break;
             }
         }
+
+        if(value.u == rego){  // rewent认为是正常执行
+            do_else = false;
+        }
     }
     if(do_else){
         GWARF_result tmp_result = traverse(the_statement->code.while_cycle.else_do, the_var, false, global_inter);
@@ -1926,7 +1951,11 @@ GWARF_result assignment_statement_core(statement *the_statement, var_list *the_v
         right_result.value.lock_token = base;
     }
 
-    if(the_statement->type == base_var){  // 通过base_var赋值
+    if(the_statement == NULL){
+        value = right_result;
+        value.base_name = NULL;  // 默认是NULL
+    }
+    else if(the_statement->type == base_var){  // 通过base_var赋值
         char *left = the_statement->code.base_var.var_name;  // get var name but not value
         int from = 0;
         if(the_statement->code.base_var.from == NULL){
@@ -1984,18 +2013,22 @@ GWARF_result assignment_statement_core(statement *the_statement, var_list *the_v
         GWARF_value base_the_var = tmp_result.value;  // 不用取value
         if(base_the_var.type == CLASS_value){
             value = assignment_statement(the_statement->code.point.child_var, the_var, base_the_var.value.class_value->the_var, right_result,global_inter);
+            value.base_name = NULL;  // 默认是NULL
         }
         else if(base_the_var.type == OBJECT_value){
             value = assignment_statement(the_statement->code.point.child_var, the_var, base_the_var.value.object_value->the_var, right_result,global_inter);
+            value.base_name = NULL;  // 默认是NULL
         }
         else if(base_the_var.type == FUNC_value){
             value = assignment_statement(the_statement->code.point.child_var, the_var, base_the_var.value.func_value->self, right_result,global_inter);
+            value.base_name = NULL;  // 默认是NULL
         }
         else if(base_the_var.type == NULL_value){
             return value;  // 对NONE的point运算均为NULL
         }
         else{
-            return value;  // 对NONE的point运算均为NULL
+            value = to_error("Type Not Support The Point", "TypeException",global_inter);  // 赋值错误
+            value.base_name = NULL;  // 默认是NULL
         }
     }
     else if(the_statement->type == down){  // 通过down赋值
@@ -2011,6 +2044,7 @@ GWARF_result assignment_statement_core(statement *the_statement, var_list *the_v
                 parameter *tmp = the_statement->code.down.child_var;
                 tmp->next = pack_value_parameter(right_result.value);
                 value = call_back_core(get, the_var, tmp, global_inter);
+                value.base_name = NULL;  // 默认是NULL
                 goto the_else;
             }
         }
@@ -2022,6 +2056,7 @@ GWARF_result assignment_statement_core(statement *the_statement, var_list *the_v
                 parameter *tmp = the_statement->code.down.child_var;
                 tmp->next = pack_value_parameter(right_result.value);
                 value = call_back_core(get, the_var, tmp, global_inter);
+                value.base_name = NULL;  // 默认是NULL
             }
             else{
                 goto the_else;
@@ -2029,7 +2064,7 @@ GWARF_result assignment_statement_core(statement *the_statement, var_list *the_v
         }
         else{
             the_else: value = to_error("Bad Assignment", "AssignmentException",global_inter);  // 赋值错误
-            puts("Bad Assignment");
+            value.base_name = NULL;  // 默认是NULL
         }
     }
     else if(the_statement->type == base_svar){  // 通过base_svar赋值

+ 89 - 28
paser/syntax.c

@@ -836,6 +836,7 @@ void do_while_(p_status *status, token_node *list){
     fprintf(status_log, "[info][grammar]  mode status: while_\n");
     token do_t, while_t, exp_t, block_t, next_t, child_t, new_token;
     do_t = pop_node(list);
+    int mode = 0;  // mode为1模式需要push enter
     if(do_t.type == DO_PASER){
         get_right_token(status,list,block_,block_t);
         if(block_t.type != NON_block){  // 不是表达式
@@ -849,46 +850,50 @@ void do_while_(p_status *status, token_node *list){
             back_again(list,while_t);
             tmp->type = code_block;
             tmp->code.code_block.done = block_t.data.statement_value;
+            mode = 0;
         }
         else{
             get_right_token(status,list,top_exp,exp_t);
             if(exp_t.type != NON_top_exp){  // 不是表达式
                 paser_error("Don't get 'top_exp'");
             }
+
+            statement *else_do = NULL;
+            el_again: 
+            get_pop_token(status,list,next_t);
+            if(next_t.type == ENTER_PASER){  // 忽略Enter
+                goto el_again;
+            }
+            if(next_t.type == ELSE_PASER){  // else
+                get_right_token(status,list,block_,child_t);
+                if(child_t.type != NON_block){
+                    paser_error("Don't get '{'\n");
+                }
+                else_do = child_t.data.statement_value;
+            }
+            else{
+                back_again(list, next_t);  // 下一次读取需要用safe_get_token
+            }
+        
             tmp->type = while_cycle;
             tmp->code.while_cycle.condition = exp_t.data.statement_value;
             tmp->code.while_cycle.done = block_t.data.statement_value;
             tmp->code.while_cycle.first_do = true;
+            tmp->code.while_cycle.else_do = else_do;
+            mode = 1;
         }
 
-        statement *else_do = NULL;
-        el_again: 
-        get_pop_token(status,list,next_t);
-        if(next_t.type == ENTER_PASER){  // 忽略Enter
-            goto el_again;
-        }
-        if(next_t.type == ELSE_PASER){  // else
-            get_right_token(status,list,block_,child_t);
-            if(child_t.type != NON_block){
-                paser_error("Don't get '{'\n");
-            }
-            else_do = child_t.data.statement_value;
-        }
-        else{
-            back_again(list, next_t);  // 下一次读取需要用safe_get_token
-        }
-
-        tmp->code.while_cycle.else_do = else_do;
-
         new_token.type = NON_do_while;
         new_token.data_type = statement_value;
         new_token.data.statement_value = tmp;
         add_node(list, new_token);  // 压入节点[弹出3个压入1个]
 
-        token tmp_enter;
-        tmp_enter.type = ENTER_PASER;
-        tmp_enter.data_type = empty;
-        back_again(list, tmp_enter);  // push入一个ENTER
+        if(mode){
+            token tmp_enter;
+            tmp_enter.type = ENTER_PASER;
+            tmp_enter.data_type = empty;
+            back_again(list, tmp_enter);  // push入一个ENTER
+        }
 
         return;
     }
@@ -963,7 +968,10 @@ try_ : TRY block EXCEPT AS top_exp block
 */
 void try_(p_status *status, token_node *list){
     fprintf(status_log, "[info][grammar]  mode status: while_\n");
-    token try_t, try_block, except_t, as_t, var_t, except_block, new_token;
+    token try_t, try_block, except_t, as_t, var_t, except_block, child_t, next_t, new_token;
+    statement *else_do = NULL ,*finally_do = NULL, *except_do = NULL, *var_do = NULL;
+    bool mode_else = true, mode_finally = true;
+
     try_t = pop_node(list);
     if(try_t.type == TRY_PASER){
         get_right_token(status, list, block_, try_block);
@@ -977,34 +985,87 @@ void try_(p_status *status, token_node *list){
             goto except_again;
         }
         else if(except_t.type != EXCEPT_PASER){  // 不是except
-            paser_error("Don't get 'except'");
+            back_again(list, except_t);
+            goto el_again;
         }
 
         get_pop_token(status,list,as_t);
         if(as_t.type != AS_PASER){  // 不是except
-            paser_error("Don't get 'as'");
+            back_again(list, as_t);
+            goto not_var;
         }
 
         get_right_token(status, list, top_exp, var_t);
         if(var_t.type != NON_top_exp){
             paser_error("Don't get top_exp");
         }
+        else{
+            var_do = var_t.data.statement_value;
+        }
 
+        not_var:
         get_right_token(status,list,block_,except_block);
         if(except_block.type != NON_block){  // 不是表达式
             paser_error("Don't get '{'");
         }
+        else{
+            except_do = except_block.data.statement_value;
+        }
+
+        el_again: 
+        get_pop_token(status,list,next_t);
+        if(next_t.type == ENTER_PASER){  // 忽略Enter
+            goto el_again;
+        }
+        if(next_t.type == ELSE_PASER){  // else
+            if(mode_else){
+                get_right_token(status,list,block_,child_t);
+                if(child_t.type != NON_block){
+                    paser_error("Don't get '{'\n");
+                }
+                else_do = child_t.data.statement_value;
+                mode_else = false;
+                goto el_again;
+            }
+            else{
+                paser_error("Get 'else' twict\n");
+            }
+        }
+        if(next_t.type == FINALLY_PASER){  // else
+            if(mode_finally){
+                get_right_token(status,list,block_,child_t);
+                if(child_t.type != NON_block){
+                    paser_error("Don't get '{'\n");
+                }
+                finally_do = child_t.data.statement_value;
+                mode_finally = false;
+                goto el_again;
+            }
+            else{
+                paser_error("Get 'finally' twict\n");
+            }
+        }
+        else{
+            back_again(list, next_t);  // 下一次读取需要用safe_get_token
+        }
 
         statement *try_tmp =  make_statement();
         try_tmp->type = try_code;
         try_tmp->code.try_code.try = try_block.data.statement_value;
-        try_tmp->code.try_code.except = except_block.data.statement_value;
-        try_tmp->code.try_code.var = var_t.data.statement_value;
+        try_tmp->code.try_code.except = except_do;
+        try_tmp->code.try_code.var = var_do;
+        try_tmp->code.try_code.else_do = else_do;
+        try_tmp->code.try_code.finally_do = finally_do;
 
         new_token.type = NON_try;
         new_token.data_type = statement_value;
         new_token.data.statement_value = try_tmp;
         add_node(list, new_token);  // 压入节点[弹出3个压入1个]
+
+        token tmp_enter;
+        tmp_enter.type = ENTER_PASER;
+        tmp_enter.data_type = empty;
+        back_again(list, tmp_enter);  // push入一个ENTER
         return;
     }
     else{