update
This commit is contained in:
parent
6fcd3ecdc0
commit
7f73a2f5ae
|
@ -31,6 +31,15 @@ void logo()
|
|||
return;
|
||||
}
|
||||
|
||||
void del_func()
|
||||
{
|
||||
resource.clear();
|
||||
lexer.clear();
|
||||
parse.clear();
|
||||
std::cout<<">> [Delete] complete."<<std::endl;
|
||||
return;
|
||||
}
|
||||
|
||||
void lex_func()
|
||||
{
|
||||
lexer.scanner(resource.get_file());
|
||||
|
@ -92,12 +101,7 @@ int main()
|
|||
#endif
|
||||
}
|
||||
else if(command=="del")
|
||||
{
|
||||
resource.delete_file();
|
||||
lexer.delete_tokens();
|
||||
parse.clear();
|
||||
std::cout<<">> [Delete] complete."<<std::endl;
|
||||
}
|
||||
del_func();
|
||||
else if(command=="lib")
|
||||
resource.load_lib();
|
||||
else if(command=="rs")
|
||||
|
|
|
@ -39,20 +39,19 @@ expressions::=
|
|||
'{' {expr} '}'
|
||||
;
|
||||
calculation::=
|
||||
'(' calculation ')'
|
||||
|scalar
|
||||
|trinocular
|
||||
|and_expr
|
||||
|or_expr
|
||||
|calculation ('=' | '+=' | '-=' | '*=' | '/=' | '~=') calculation
|
||||
;
|
||||
trinocular::=
|
||||
calculation '?' calculation ':' calculation
|
||||
;
|
||||
and_expr::=
|
||||
or_expr and or_expr
|
||||
;
|
||||
or_expr::=
|
||||
cmp_expr or cmp_expr
|
||||
and_expr or and_expr
|
||||
;
|
||||
and_expr::=
|
||||
cmp_expr and cmp_expr
|
||||
;
|
||||
cmp_expr::=
|
||||
additive_expr ('==' | '!=' | '>' | '<' | '>=' | '<=') additive_expr
|
||||
|
@ -61,10 +60,10 @@ additive_expr::=
|
|||
multive_expr ('+' | '-' | '~') multive_expr
|
||||
;
|
||||
multive_expr::=
|
||||
unary ('*' | '/') unary
|
||||
(unary|scalar) ('*' | '/') (unary|scalar)
|
||||
;
|
||||
unary::=
|
||||
('-'|'!') calculation
|
||||
('-'|'!') scalar
|
||||
;
|
||||
scalar::=
|
||||
function_call
|
||||
|
@ -73,6 +72,7 @@ scalar::=
|
|||
|hash_call
|
||||
|number
|
||||
|string
|
||||
|'(' calculation ')'
|
||||
;
|
||||
function_call::=
|
||||
function {call_scalar}
|
||||
|
@ -112,9 +112,18 @@ multi_assignment::=
|
|||
multi_scalar '=' multi_scalar
|
||||
;
|
||||
loop::=
|
||||
while_loop
|
||||
|for_loop
|
||||
|forei_loop
|
||||
;
|
||||
while_loop::=
|
||||
while '(' calculation ')' expressions
|
||||
|for '(' [definition] ';' [calculation] ';' [calculation] ')' expressions
|
||||
|(forindex | foreach) '(' (definition | assignment) ';' calculation ')' expressions
|
||||
;
|
||||
for_loop::=
|
||||
for '(' [definition] ';' [calculation] ';' [calculation] ')' expressions
|
||||
;
|
||||
forei_loop::=
|
||||
(forindex | foreach) '(' (definition | assignment) ';' calculation ')' expressions
|
||||
;
|
||||
conditional::=
|
||||
if '(' calculation ')' expressions
|
||||
|
|
|
@ -24,8 +24,13 @@ enum ast_node
|
|||
ast_nil,ast_number,ast_string,ast_identifier,ast_function,ast_hash,ast_vector,
|
||||
ast_hashmember,
|
||||
ast_args,
|
||||
ast_and,ast_or,
|
||||
ast_equal,ast_add_equal,ast_sub_equal,ast_mult_equal,ast_div_equal,ast_link_equal,
|
||||
ast_cmp_equal,ast_cmp_not_equal,ast_less_than,ast_less_equal,ast_greater_than,ast_greater_equal,
|
||||
ast_add,ast_sub,ast_mult,ast_div,ast_link,
|
||||
ast_unary_sub,ast_unary_not,
|
||||
ast_for,ast_forindex,ast_foreach,ast_while,
|
||||
ast_definition,ast_assignment,ast_calculation,
|
||||
ast_definition,ast_multi_assign,ast_calculation,
|
||||
ast_continue,ast_break,ast_return,
|
||||
};
|
||||
|
||||
|
@ -35,6 +40,7 @@ enum parse_error
|
|||
error_token,
|
||||
lack_id,
|
||||
lack_left_curve,
|
||||
lack_right_curve,
|
||||
lack_left_bracket,
|
||||
lack_left_brace,
|
||||
lack_right_brace,
|
||||
|
@ -54,7 +60,8 @@ void error_info(int line,int error_type)
|
|||
case unknown: detail="unknown error."; break;
|
||||
case error_token: detail="this token should not exist here."; break;
|
||||
case lack_id: detail="lack identifier."; break;
|
||||
case lack_left_curve: detail="lack left curve."; break;
|
||||
case lack_left_curve: detail="lack \'(\'."; break;
|
||||
case lack_right_curve: detail="lack \')\'."; break;
|
||||
case lack_left_bracket: detail="lack left bracket."; break;
|
||||
case lack_left_brace: detail="lack left brace."; break;
|
||||
case lack_right_brace: detail="lack right brace."; break;
|
||||
|
|
|
@ -85,14 +85,14 @@ private:
|
|||
std::string number_gen(std::vector<char>&,int&,int&);
|
||||
std::string string_gen(std::vector<char>&,int&,int&);
|
||||
public:
|
||||
void delete_tokens();
|
||||
void clear();
|
||||
void scanner(std::vector<char>&);
|
||||
void print_token();
|
||||
int get_error();
|
||||
std::vector<token>& get_token_list();
|
||||
};
|
||||
|
||||
void nasal_lexer::delete_tokens()
|
||||
void nasal_lexer::clear()
|
||||
{
|
||||
token_list.clear();
|
||||
return;
|
||||
|
|
|
@ -10,6 +10,7 @@ private:
|
|||
nasal_ast root;
|
||||
std::vector<token> tok_list;
|
||||
void reset();
|
||||
bool check_function_end(nasal_ast&);
|
||||
nasal_ast nil_gen();
|
||||
nasal_ast number_gen();
|
||||
nasal_ast string_gen();
|
||||
|
@ -23,8 +24,8 @@ private:
|
|||
nasal_ast exprs_gen();
|
||||
nasal_ast calculation();
|
||||
nasal_ast trinocular();
|
||||
nasal_ast and_expr();
|
||||
nasal_ast or_expr();
|
||||
nasal_ast and_expr();
|
||||
nasal_ast cmp_expr();
|
||||
nasal_ast additive_expr();
|
||||
nasal_ast multive_expr();
|
||||
|
@ -96,6 +97,17 @@ void nasal_parse::reset()
|
|||
return;
|
||||
}
|
||||
|
||||
bool nasal_parse::check_function_end(nasal_ast& node)
|
||||
{
|
||||
if(node.get_type()==ast_function)
|
||||
return true;
|
||||
if(node.get_children().empty() || (node.get_type()!=ast_definition && node.get_type()!=ast_equal))
|
||||
return false;
|
||||
else
|
||||
return check_function_end(node.get_children().back());
|
||||
return false;
|
||||
}
|
||||
|
||||
nasal_ast nasal_parse::nil_gen()
|
||||
{
|
||||
nasal_ast node;
|
||||
|
@ -245,31 +257,26 @@ nasal_ast nasal_parse::expr()
|
|||
node.set_line(tok_list[ptr].line);
|
||||
switch(tok_list[ptr].type)
|
||||
{
|
||||
case tok_nil:case tok_number:case tok_string:case tok_identifier:
|
||||
case tok_nil:
|
||||
case tok_number:
|
||||
case tok_string:
|
||||
case tok_identifier:
|
||||
case tok_func:
|
||||
case tok_left_bracket:case tok_left_brace:
|
||||
case tok_left_bracket:
|
||||
case tok_left_brace:
|
||||
case tok_sub:
|
||||
case tok_not: node=calculation(); break;
|
||||
case tok_var: node=definition(); break;
|
||||
case tok_for:case tok_forindex:case tok_foreach:
|
||||
case tok_while: node=loop(); break;
|
||||
case tok_if: node=conditional(); break;
|
||||
case tok_continue:break;
|
||||
case tok_break:break;
|
||||
case tok_return:break;
|
||||
case tok_semi:--ptr;break;
|
||||
defaut: error_info(tok_list[ptr].line,error_token);++error;break;
|
||||
}
|
||||
++ptr;
|
||||
if(ptr>=tok_list_size || (ptr<tok_list_size && tok_list[ptr].type!=tok_semi))
|
||||
{
|
||||
bool tmp=node.get_children().empty();
|
||||
if(tmp || (!tmp && node.get_children().back().get_type()!=ast_function))
|
||||
{
|
||||
error_info(node.get_children().back().get_line(),lack_semi);
|
||||
++error;
|
||||
}
|
||||
if(ptr<tok_list_size) --ptr;
|
||||
case tok_not: node=calculation(); break;
|
||||
case tok_var: node=definition(); break;
|
||||
case tok_for:
|
||||
case tok_forindex:
|
||||
case tok_foreach:
|
||||
case tok_while: node=loop(); break;
|
||||
case tok_if: node=conditional(); break;
|
||||
case tok_continue: node=continue_expr(); break;
|
||||
case tok_break: node=break_expr(); break;
|
||||
case tok_return: node=return_expr(); break;
|
||||
case tok_semi: --ptr; break;
|
||||
default: error_info(tok_list[ptr].line,error_token);++error;break;
|
||||
}
|
||||
return node;
|
||||
}
|
||||
|
@ -284,6 +291,12 @@ nasal_ast nasal_parse::exprs_gen()
|
|||
{
|
||||
node.add_child(expr());
|
||||
++ptr;
|
||||
if(ptr<tok_list_size && tok_list[ptr].type==tok_semi) ++ptr;
|
||||
else if(ptr<tok_list_size && (node.get_children().empty() || !check_function_end(node.get_children().back())))
|
||||
{
|
||||
++error;
|
||||
error_info(tok_list[ptr].line,lack_semi);
|
||||
}
|
||||
}
|
||||
if(ptr>=tok_list_size)
|
||||
{
|
||||
|
@ -292,13 +305,19 @@ nasal_ast nasal_parse::exprs_gen()
|
|||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
node.add_child(expr());
|
||||
++ptr;
|
||||
if(ptr>=tok_list_size || tok_list[ptr].type!=tok_semi)
|
||||
--ptr;
|
||||
}
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::calculation()
|
||||
{
|
||||
nasal_ast node;
|
||||
node.set_line(tok_list[ptr].line);
|
||||
int tok_type=tok_list[ptr].type;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::trinocular()
|
||||
|
@ -306,39 +325,171 @@ nasal_ast nasal_parse::trinocular()
|
|||
nasal_ast node;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::and_expr()
|
||||
{
|
||||
nasal_ast node;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::or_expr()
|
||||
{
|
||||
nasal_ast node;
|
||||
node=and_expr();
|
||||
++ptr;
|
||||
while(ptr<tok_list_size && tok_list[ptr].type==tok_or)
|
||||
{
|
||||
nasal_ast tmp;
|
||||
tmp.set_line(tok_list[ptr].line);
|
||||
tmp.set_type(ast_or);
|
||||
tmp.add_child(node);
|
||||
++ptr;
|
||||
tmp.add_child(and_expr());
|
||||
node=tmp;
|
||||
++ptr;
|
||||
}
|
||||
--ptr;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::and_expr()
|
||||
{
|
||||
nasal_ast node;
|
||||
node=cmp_expr();
|
||||
++ptr;
|
||||
while(ptr<tok_list_size && tok_list[ptr].type==tok_and)
|
||||
{
|
||||
nasal_ast tmp;
|
||||
tmp.set_line(tok_list[ptr].line);
|
||||
tmp.set_type(ast_and);
|
||||
tmp.add_child(node);
|
||||
++ptr;
|
||||
tmp.add_child(cmp_expr());
|
||||
node=tmp;
|
||||
++ptr;
|
||||
}
|
||||
--ptr;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::cmp_expr()
|
||||
{
|
||||
nasal_ast node;
|
||||
node=additive_expr();
|
||||
++ptr;
|
||||
while(
|
||||
ptr<tok_list_size &&
|
||||
(
|
||||
tok_list[ptr].type==tok_cmp_equal ||
|
||||
tok_list[ptr].type==tok_cmp_not_equal ||
|
||||
tok_list[ptr].type==tok_less_than ||
|
||||
tok_list[ptr].type==tok_less_equal ||
|
||||
tok_list[ptr].type==tok_greater_than ||
|
||||
tok_list[ptr].type==tok_greater_equal
|
||||
)
|
||||
)
|
||||
{
|
||||
nasal_ast tmp;
|
||||
tmp.set_line(tok_list[ptr].line);
|
||||
switch(tok_list[ptr].type)
|
||||
{
|
||||
case tok_cmp_equal: tmp.set_type(ast_cmp_equal); break;
|
||||
case tok_cmp_not_equal: tmp.set_type(ast_cmp_not_equal); break;
|
||||
case tok_less_than: tmp.set_type(ast_less_than); break;
|
||||
case tok_less_equal: tmp.set_type(ast_less_equal); break;
|
||||
case tok_greater_than: tmp.set_type(ast_greater_than); break;
|
||||
case tok_greater_equal: tmp.set_type(ast_greater_equal); break;
|
||||
}
|
||||
tmp.add_child(node);
|
||||
++ptr;
|
||||
tmp.add_child(additive_expr());
|
||||
node=tmp;
|
||||
++ptr;
|
||||
}
|
||||
--ptr;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::additive_expr()
|
||||
{
|
||||
nasal_ast node;
|
||||
node=multive_expr();
|
||||
++ptr;
|
||||
while(ptr<tok_list_size && (tok_list[ptr].type==tok_add || tok_list[ptr].type==tok_sub || tok_list[ptr].type==tok_link))
|
||||
{
|
||||
nasal_ast tmp;
|
||||
tmp.set_line(tok_list[ptr].line);
|
||||
switch(tok_list[ptr].type)
|
||||
{
|
||||
case tok_add: tmp.set_type(ast_add); break;
|
||||
case tok_sub: tmp.set_type(ast_sub); break;
|
||||
case tok_link: tmp.set_type(ast_link); break;
|
||||
}
|
||||
tmp.add_child(node);
|
||||
++ptr;
|
||||
tmp.add_child(multive_expr());
|
||||
node=tmp;
|
||||
++ptr;
|
||||
}
|
||||
--ptr;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::multive_expr()
|
||||
{
|
||||
nasal_ast node;
|
||||
if(tok_list[ptr].type==tok_sub || tok_list[ptr].type==tok_not)
|
||||
node=unary();
|
||||
++ptr;
|
||||
while(ptr<tok_list_size && (tok_list[ptr].type==tok_mult || tok_list[ptr].type==tok_div))
|
||||
{
|
||||
nasal_ast tmp;
|
||||
tmp.set_line(tok_list[ptr].line);
|
||||
switch(tok_list[ptr].type)
|
||||
{
|
||||
case tok_mult:tmp.set_type(ast_mult);break;
|
||||
case tok_div: tmp.set_type(ast_div); break;
|
||||
}
|
||||
tmp.add_child(node);
|
||||
++ptr;
|
||||
if(ptr<tok_list_size && (tok_list[ptr].type==tok_sub || tok_list[ptr].type==tok_not))
|
||||
tmp.add_child(unary());
|
||||
else if(ptr<tok_list_size && tok_list[ptr].type!=tok_sub && tok_list[ptr].type!=tok_not)
|
||||
tmp.add_child(scalar());
|
||||
node=tmp;
|
||||
++ptr;
|
||||
}
|
||||
--ptr;
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::unary()
|
||||
{
|
||||
nasal_ast node;
|
||||
node.set_line(tok_list[ptr].line);
|
||||
switch(tok_list[ptr].type)
|
||||
{
|
||||
case tok_sub:node.set_type(ast_unary_sub);break;
|
||||
case tok_not:node.set_type(ast_unary_not);break;
|
||||
}
|
||||
node.add_child(scalar());
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::scalar()
|
||||
{
|
||||
nasal_ast node;
|
||||
node.set_line(tok_list[ptr].line);
|
||||
if(tok_list[ptr].type==tok_number)
|
||||
node=number_gen();
|
||||
else if(tok_list[ptr].type==tok_string)
|
||||
node=string_gen();
|
||||
else if(
|
||||
tok_list[ptr].type==tok_func ||
|
||||
tok_list[ptr].type==tok_identifier ||
|
||||
tok_list[ptr].type==tok_left_bracket ||
|
||||
tok_list[ptr].type==tok_left_brace
|
||||
)
|
||||
node=call_scalar();
|
||||
else if(tok_list[ptr].type==tok_left_curve)
|
||||
{
|
||||
int curve_line=tok_list[ptr].line;
|
||||
++ptr;
|
||||
node=calculation();
|
||||
++ptr;
|
||||
if(ptr>=tok_list_size || tok_list[ptr].type!=tok_right_curve)
|
||||
{
|
||||
++error;
|
||||
error_info(curve_line,lack_right_curve);
|
||||
}
|
||||
}
|
||||
return node;
|
||||
}
|
||||
nasal_ast nasal_parse::func_call()
|
||||
|
|
|
@ -27,7 +27,7 @@ private:
|
|||
public:
|
||||
void input_file(std::string);
|
||||
void load_lib();
|
||||
void delete_file();
|
||||
void clear();
|
||||
void print_file();
|
||||
std::vector<char>& get_file();
|
||||
};
|
||||
|
@ -58,7 +58,7 @@ void nasal_resource::load_lib()
|
|||
return;
|
||||
}
|
||||
|
||||
void nasal_resource::delete_file()
|
||||
void nasal_resource::clear()
|
||||
{
|
||||
res.clear();
|
||||
return;
|
||||
|
|
Loading…
Reference in New Issue