Complete parser

This commit is contained in:
Valk Richard Li
2019-11-05 23:57:00 +08:00
committed by GitHub
parent 75542785aa
commit eb6645deaa
3 changed files with 463 additions and 105 deletions
+458 -112
View File
@@ -69,56 +69,217 @@ class balloon_parse
{ {
return error; return error;
} }
void definition(); void print_generated_tree()
void assignment(); {
void array_generate(); std::cout<<">>[Abstract-syntax-tree]"<<std::endl;
void hash_generate(); root.print_tree(1);
void check_number(); return;
void check_string(); }
void check_unary(); abstract_syntax_tree ret();
void block(); abstract_syntax_tree choose();
void func_generate(); abstract_syntax_tree loop();
void call_identifier(); abstract_syntax_tree definition();
void calculation(); abstract_syntax_tree assignment();
void calculation_or(); abstract_syntax_tree array_generate();
void calculation_and(); abstract_syntax_tree hash_generate();
void calculation_cmp(); abstract_syntax_tree check_number();
void calculation_additive(); abstract_syntax_tree check_string();
void calculation_multive(); abstract_syntax_tree check_unary();
void scalar(); abstract_syntax_tree block();
abstract_syntax_tree func_generate();
abstract_syntax_tree call_identifier();
abstract_syntax_tree calculation();
abstract_syntax_tree calculation_or();
abstract_syntax_tree calculation_and();
abstract_syntax_tree calculation_cmp();
abstract_syntax_tree calculation_additive();
abstract_syntax_tree calculation_multive();
abstract_syntax_tree scalar();
void check_semi(); void check_semi();
void parse_main(); void parse_main();
}; };
void balloon_parse::definition() abstract_syntax_tree balloon_parse::ret()
{ {
abstract_syntax_tree new_node;
new_node.set_type(__return);
get_token();
if(this_token.type!=__return)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": must use \'return\' here."<<std::endl;
return new_node;
}
get_token();
if(this_token.type==__semi)
parse.push(this_token);
else
{
parse.push(this_token);
new_node.add_child(scalar());
}
return new_node;
}
abstract_syntax_tree balloon_parse::choose()
{
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node.set_type(__ifelse);
temp.set_type(__if);
get_token();
if(this_token.type!=__if)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": must use \'if\' when generating an if-else statement."<<std::endl;
return new_node;
}
get_token();
if(this_token.type!=__left_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'(\'."<<std::endl;
return new_node;
}
temp.add_child(scalar());
get_token();
if(this_token.type!=__right_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\'."<<std::endl;
return new_node;
}
temp.add_child(block());
new_node.add_child(temp);
while(1)
{
temp.set_clear();
get_token();
if(this_token.type!=__elsif && this_token.type!=__else)
break;
if(this_token.type==__else)
{
get_token();
if(this_token.type==__if)// else if
{
temp.set_type(__elsif);
get_token();
if(this_token.type!=__left_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'(\'."<<std::endl;
return new_node;
}
temp.add_child(scalar());
get_token();
if(this_token.type!=__right_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\'."<<std::endl;
return new_node;
}
temp.add_child(block());
}
else// real else
{
temp.set_type(__else);
parse.push(this_token);
temp.add_child(block());
break;
}
new_node.add_child(temp);
}
else if(this_token.type==__elsif)
{
temp.set_type(__elsif);
get_token();
if(this_token.type!=__left_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'(\'."<<std::endl;
return new_node;
}
temp.add_child(scalar());
get_token();
if(this_token.type!=__right_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\'."<<std::endl;
return new_node;
}
temp.add_child(block());
new_node.add_child(temp);
}
}
return new_node;
}
abstract_syntax_tree balloon_parse::loop()
{
abstract_syntax_tree new_node;
new_node.set_type(__while);
get_token();
if(this_token.type!=__while)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": must use \'while\' when generating a loop."<<std::endl;
return new_node;
}
get_token();
if(this_token.type!=__left_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'(\'."<<std::endl;
return new_node;
}
new_node.add_child(scalar());
get_token();
if(this_token.type!=__right_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\'."<<std::endl;
return new_node;
}
new_node.add_child(block());
return new_node;
}
abstract_syntax_tree balloon_parse::definition()
{
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node.set_type(__definition);
temp.set_type(__id);
get_token(); get_token();
if(this_token.type!=__var) if(this_token.type!=__var)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'var\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'var\' here."<<std::endl;
return; return new_node;
} }
get_token(); get_token();
if(this_token.type!=__id) if(this_token.type!=__id)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect an identifier here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect an identifier here."<<std::endl;
return; return new_node;
} }
temp.set_name(this_token.str);
new_node.add_child(temp);
get_token(); get_token();
if(this_token.type!=__equal) if(this_token.type!=__equal)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'=\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'=\' here."<<std::endl;
return; return new_node;
} }
scalar(); new_node.add_child(scalar());
return; return new_node;
} }
void balloon_parse::assignment() abstract_syntax_tree balloon_parse::assignment()
{ {
abstract_syntax_tree new_node;
get_token(); get_token();
if(!(this_token.type==__equal || this_token.type==__add_equal if(!(this_token.type==__equal || this_token.type==__add_equal
|| this_token.type==__sub_equal || this_token.type==__mul_equal || this_token.type==__sub_equal || this_token.type==__mul_equal
@@ -126,20 +287,23 @@ void balloon_parse::assignment()
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect an operator for assignment here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect an operator for assignment here."<<std::endl;
return; return new_node;
} }
scalar(); new_node.set_type(this_token.type);
return; new_node.add_child(scalar());
return new_node;
} }
void balloon_parse::array_generate() abstract_syntax_tree balloon_parse::array_generate()
{ {
abstract_syntax_tree new_node;
new_node.set_type(__array);
get_token(); get_token();
if(this_token.type!=__left_bracket) if(this_token.type!=__left_bracket)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'[\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'[\' here."<<std::endl;
return; return new_node;
} }
get_token(); get_token();
if(this_token.type!=__right_bracket) if(this_token.type!=__right_bracket)
@@ -157,12 +321,12 @@ void balloon_parse::array_generate()
case __sub_operator: case __sub_operator:
case __number: case __number:
case __string: case __string:
case __id:parse.push(this_token);scalar();break; case __id:parse.push(this_token);new_node.add_child(scalar());break;
case __right_bracket:parse.push(this_token);break; case __right_bracket:parse.push(this_token);break;
default: default:
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar or \']\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar or \']\' here."<<std::endl;
return; return new_node;
break; break;
} }
get_token(); get_token();
@@ -170,39 +334,45 @@ void balloon_parse::array_generate()
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \',\' or \']\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \',\' or \']\' here."<<std::endl;
return; return new_node;
} }
} }
return; return new_node;
} }
void balloon_parse::hash_generate() abstract_syntax_tree balloon_parse::hash_generate()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node.set_type(__hash);
get_token(); get_token();
if(this_token.type!=__left_brace) if(this_token.type!=__left_brace)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'{\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'{\' here."<<std::endl;
return; return new_node;
} }
get_token(); get_token();
if(this_token.type!=__right_brace) if(this_token.type!=__right_brace)
parse.push(this_token); parse.push(this_token);
while(this_token.type!=__right_brace) while(this_token.type!=__right_brace)
{ {
temp.set_clear();
temp.set_type(__id);
get_token(); get_token();
if(this_token.type!=__id) if(this_token.type!=__id)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect an identifier here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect an identifier here."<<std::endl;
return; return new_node;
} }
temp.set_name(this_token.str);
get_token(); get_token();
if(this_token.type!=__colon) if(this_token.type!=__colon)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \':\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \':\' here."<<std::endl;
return; return new_node;
} }
get_token(); get_token();
switch(this_token.type) switch(this_token.type)
@@ -215,102 +385,147 @@ void balloon_parse::hash_generate()
case __sub_operator: case __sub_operator:
case __number: case __number:
case __string: case __string:
case __id:parse.push(this_token);scalar();break; case __id:parse.push(this_token);temp.add_child(scalar());break;
case __right_brace:parse.push(this_token);break; case __right_brace:parse.push(this_token);break;
default: default:
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar or \'}\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar or \'}\' here."<<std::endl;
return; return new_node;
break; break;
} }
new_node.add_child(temp);
get_token(); get_token();
if(this_token.type!=__comma && this_token.type!=__right_brace) if(this_token.type!=__comma && this_token.type!=__right_brace)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \',\' or \'}\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \',\' or \'}\' here."<<std::endl;
return; return new_node;
} }
} }
return; return new_node;
} }
void balloon_parse::check_number() abstract_syntax_tree balloon_parse::check_number()
{ {
abstract_syntax_tree new_node;
new_node.set_type(__number);
get_token(); get_token();
if(this_token.type!=__number) if(this_token.type!=__number)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a number here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a number here."<<std::endl;
return new_node;
} }
return; new_node.set_number(this_token.str);
return new_node;
} }
void balloon_parse::check_string() abstract_syntax_tree balloon_parse::check_string()
{ {
abstract_syntax_tree new_node;
new_node.set_type(__string);
get_token(); get_token();
if(this_token.type!=__string) if(this_token.type!=__string)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a string here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a string here."<<std::endl;
return new_node;
} }
return; new_node.set_string(this_token.str);
return new_node;
} }
void balloon_parse::check_unary() abstract_syntax_tree balloon_parse::check_unary()
{ {
abstract_syntax_tree new_node;
get_token(); get_token();
if(this_token.type!=__nor_operator && this_token.type!=__sub_operator) if(this_token.type!=__nor_operator && this_token.type!=__sub_operator)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a unary operator here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a unary operator here."<<std::endl;
return new_node;
} }
new_node.set_type(this_token.type);
get_token(); get_token();
switch(this_token.type) switch(this_token.type)
{ {
case __number:parse.push(this_token);check_number();break; case __number:parse.push(this_token);new_node.add_child(check_number());break;
case __string:parse.push(this_token);check_string();break; case __string:parse.push(this_token);new_node.add_child(check_string());break;
case __id:parse.push(this_token);call_identifier();break; case __id:parse.push(this_token);new_node.add_child(call_identifier());break;
case __left_curve:parse.push(this_token);scalar();break; case __left_curve:parse.push(this_token);new_node.add_child(scalar());break;
case __nor_operator:parse.push(this_token);check_unary();break; case __nor_operator:parse.push(this_token);new_node.add_child(check_unary());break;
default:++error;std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar here."<<std::endl;break; default:++error;std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar here."<<std::endl;break;
} }
return; return new_node;
} }
void balloon_parse::block() abstract_syntax_tree balloon_parse::block()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node.set_type(__block);
get_token(); get_token();
if(this_token.type!=__left_brace) if(this_token.type!=__left_brace)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'{\' ."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'{\' ."<<std::endl;
return; return new_node;
} }
while(this_token.type!=__right_brace) while(this_token.type!=__right_brace)
{ {
get_token(); get_token();
switch(this_token.type) switch(this_token.type)
{ {
case __var:parse.push(this_token);new_node.add_child(definition());check_semi();break;
case __left_curve:
case __left_bracket:
case __left_brace:
case __nor_operator:
case __sub_operator:
case __number:
case __string:
case __id:parse.push(this_token);new_node.add_child(scalar());check_semi();break;
case __if:parse.push(this_token);new_node.add_child(choose());break;
case __for:
case __forindex:
case __foreach:
case __while:parse.push(this_token);new_node.add_child(loop());break;
case __semi:break;
case __continue: case __continue:
case __break:check_semi();break; case __break:temp.set_clear();temp.set_type(this_token.type);new_node.add_child(temp);check_semi();break;
case __return:parse.push(this_token);new_node.add_child(ret());check_semi();break;
case __right_brace:break; case __right_brace:break;
default:
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": \'";
print_detail_token(this_token.type);
std::cout<<"\' should not appear in this scope."<<std::endl;
break;
} }
} }
return; return new_node;
} }
void balloon_parse::func_generate() abstract_syntax_tree balloon_parse::func_generate()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree para;
abstract_syntax_tree temp;
new_node.set_type(__function);
para.set_type(__parameter);
get_token(); get_token();
if(this_token.type!=__func) if(this_token.type!=__func)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'func\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \'func\' here."<<std::endl;
return; return new_node;
} }
get_token(); get_token();
if(this_token.type==__left_curve) if(this_token.type==__left_curve)
{ {
get_token();
if(this_token.type!=__right_curve)
parse.push(this_token);
while(this_token.type!=__right_curve) while(this_token.type!=__right_curve)
{ {
get_token(); get_token();
@@ -318,8 +533,12 @@ void balloon_parse::func_generate()
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect identifier when declaring a new function."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect identifier when declaring a new function."<<std::endl;
return; return new_node;
} }
temp.set_clear();
temp.set_type(this_token.type);
temp.set_name(this_token.str);
para.add_child(temp);
if(this_token.type==__dynamic_id) if(this_token.type==__dynamic_id)
{ {
get_token(); get_token();
@@ -327,7 +546,7 @@ void balloon_parse::func_generate()
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": dynamic identifier should have \')\' behind it ."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": dynamic identifier should have \')\' behind it ."<<std::endl;
return; return new_node;
} }
} }
else else
@@ -337,56 +556,75 @@ void balloon_parse::func_generate()
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect \',\' or \')\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect \',\' or \')\' here."<<std::endl;
return; return new_node;
} }
} }
} }
} }
else else
parse.push(this_token); parse.push(this_token);
block(); new_node.add_child(para);
return; new_node.add_child(block());
return new_node;
} }
void balloon_parse::call_identifier() abstract_syntax_tree balloon_parse::call_identifier()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
get_token(); get_token();
if(this_token.type!=__id) if(this_token.type!=__id)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": must have an identifier here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": must have an identifier here."<<std::endl;
return; return new_node;
} }
new_node.set_type(__id);
new_node.set_name(this_token.str);
while(1) while(1)
{ {
get_token(); get_token();
if(this_token.type==__left_curve) if(this_token.type==__left_curve)
{ {
temp.set_clear();
temp.set_type(__call_function);
get_token();
if(this_token.type!=__right_curve)
parse.push(this_token);
while(this_token.type!=__right_curve) while(this_token.type!=__right_curve)
{ {
scalar(); temp.add_child(scalar());
get_token(); get_token();
if(this_token.type!=__comma && this_token.type!=__right_curve) if(this_token.type!=__comma && this_token.type!=__right_curve)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \',\' or \')\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \',\' or \')\' here."<<std::endl;
return; return new_node;
} }
} }
new_node.add_child(temp);
} }
else if(this_token.type==__left_bracket) else if(this_token.type==__left_bracket)
{ {
scalar(); temp.set_clear();
temp.set_type(__call_array);
temp.add_child(scalar());
get_token(); get_token();
if(this_token.type!=__right_bracket) if(this_token.type!=__right_bracket)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \']\' ."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \']\' ."<<std::endl;
return; return new_node;
} }
new_node.add_child(temp);
} }
else if(this_token.type==__dot) else if(this_token.type==__dot)
call_identifier(); {
temp.set_clear();
temp=call_identifier();
temp.set_type(__call_hash);
new_node.add_child(temp);
}
else else
{ {
parse.push(this_token); parse.push(this_token);
@@ -399,54 +637,102 @@ void balloon_parse::call_identifier()
|| this_token.type==__div_equal || this_token.type==__link_equal) || this_token.type==__div_equal || this_token.type==__link_equal)
{ {
parse.push(this_token); parse.push(this_token);
assignment(); temp=new_node;
new_node=assignment();
new_node.add_child(temp);
} }
else else
parse.push(this_token); parse.push(this_token);
return; return new_node;
} }
void balloon_parse::calculation() abstract_syntax_tree balloon_parse::calculation()
{ {
calculation_or(); abstract_syntax_tree new_node;
return; new_node=calculation_or();
return new_node;
} }
void balloon_parse::calculation_or() abstract_syntax_tree balloon_parse::calculation_or()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node=calculation_and();
get_token();
if(this_token.type!=__or_operator)
{
parse.push(this_token);
return new_node;
}
temp.set_type(__or_operator);
temp.add_child(new_node);
while(1) while(1)
{ {
calculation_and(); temp.add_child(calculation_and());
new_node=temp;
temp.set_clear();
get_token(); get_token();
if(this_token.type!=__or_operator) if(this_token.type!=__or_operator)
{ {
parse.push(this_token); parse.push(this_token);
break; break;
} }
temp.set_type(__or_operator);
temp.add_child(new_node);
} }
return; return new_node;
} }
void balloon_parse::calculation_and() abstract_syntax_tree balloon_parse::calculation_and()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node=calculation_cmp();
get_token();
if(this_token.type!=__and_operator)
{
parse.push(this_token);
return new_node;
}
temp.set_type(__and_operator);
temp.add_child(new_node);
while(1) while(1)
{ {
calculation_cmp(); temp.add_child(calculation_cmp());
new_node=temp;
temp.set_clear();
get_token(); get_token();
if(this_token.type!=__and_operator) if(this_token.type!=__and_operator)
{ {
parse.push(this_token); parse.push(this_token);
break; break;
} }
temp.set_type(__and_operator);
temp.add_child(new_node);
} }
return; return new_node;
} }
void balloon_parse::calculation_cmp() abstract_syntax_tree balloon_parse::calculation_cmp()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node=calculation_additive();
get_token();
if(this_token.type!=__cmp_equal && this_token.type!=__cmp_not_equal
&& this_token.type!=__cmp_less && this_token.type!=__cmp_less_or_equal
&& this_token.type!=__cmp_more && this_token.type!=__cmp_more_or_equal)
{
parse.push(this_token);
return new_node;
}
temp.set_type(this_token.type);
temp.add_child(new_node);
while(1) while(1)
{ {
calculation_additive(); temp.add_child(calculation_additive());
new_node=temp;
temp.set_clear();
get_token(); get_token();
if(this_token.type!=__cmp_equal && this_token.type!=__cmp_not_equal if(this_token.type!=__cmp_equal && this_token.type!=__cmp_not_equal
&& this_token.type!=__cmp_less && this_token.type!=__cmp_less_or_equal && this_token.type!=__cmp_less && this_token.type!=__cmp_less_or_equal
@@ -455,82 +741,138 @@ void balloon_parse::calculation_cmp()
parse.push(this_token); parse.push(this_token);
break; break;
} }
temp.set_type(this_token.type);
temp.add_child(new_node);
} }
return new_node;
} }
void balloon_parse::calculation_additive() abstract_syntax_tree balloon_parse::calculation_additive()
{ {
abstract_syntax_tree new_node;
abstract_syntax_tree temp;
new_node=calculation_multive();
get_token();
if(this_token.type!=__add_operator && this_token.type!=__sub_operator && this_token.type!=__link_operator)
{
parse.push(this_token);
return new_node;
}
temp.set_type(this_token.type);
temp.add_child(new_node);
while(1) while(1)
{ {
calculation_multive(); temp.add_child(calculation_multive());
new_node=temp;
temp.set_clear();
get_token(); get_token();
if(this_token.type!=__add_operator && this_token.type!=__sub_operator && this_token.type!=__link_operator) if(this_token.type!=__add_operator && this_token.type!=__sub_operator && this_token.type!=__link_operator)
{ {
parse.push(this_token); parse.push(this_token);
break; break;
} }
temp.set_type(this_token.type);
temp.add_child(new_node);
} }
return; return new_node;
} }
void balloon_parse::calculation_multive() abstract_syntax_tree balloon_parse::calculation_multive()
{ {
while(1) abstract_syntax_tree new_node;
{ abstract_syntax_tree temp;
get_token(); get_token();
switch(this_token.type) switch(this_token.type)
{ {
case __left_curve: case __left_curve:
scalar();get_token(); new_node=scalar();get_token();
if(this_token.type!=__right_curve) if(this_token.type!=__right_curve)
{ {
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\' here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\' here."<<std::endl;
return; return new_node;
} }
break; break;
case __number:parse.push(this_token);check_number();break; case __number:parse.push(this_token);new_node=check_number();break;
case __string:parse.push(this_token);check_string();break; case __string:parse.push(this_token);new_node=check_string();break;
case __id:parse.push(this_token);call_identifier();break; case __id:parse.push(this_token);new_node=call_identifier();break;
case __nor_operator: case __nor_operator:
case __sub_operator:parse.push(this_token);check_unary();break; case __sub_operator:parse.push(this_token);new_node=check_unary();break;
default: default:
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar here."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar here."<<std::endl;
return; return new_node;
break; break;
} }
get_token(); get_token();
if(this_token.type!=__mul_operator && this_token.type!=__div_operator) if(this_token.type!=__mul_operator && this_token.type!=__div_operator)
{ {
parse.push(this_token); parse.push(this_token);
break; return new_node;
} }
} temp.set_type(this_token.type);
return; temp.add_child(new_node);
} while(1)
{
void balloon_parse::scalar()
{
get_token(); get_token();
switch(this_token.type) switch(this_token.type)
{ {
case __func:parse.push(this_token);func_generate();break; case __left_curve:
case __left_bracket:parse.push(this_token);array_generate();break; temp.add_child(scalar());get_token();
case __left_brace:parse.push(this_token);hash_generate();break; if(this_token.type!=__right_curve)
{
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a \')\' here."<<std::endl;
return new_node;
}
break;
case __number:parse.push(this_token);temp.add_child(check_number());break;
case __string:parse.push(this_token);temp.add_child(check_string());break;
case __id:parse.push(this_token);temp.add_child(call_identifier());break;
case __nor_operator:
case __sub_operator:parse.push(this_token);temp.add_child(check_unary());break;
default:
++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar here."<<std::endl;
return new_node;
break;
}
new_node=temp;
temp.set_clear();
get_token();
if(this_token.type!=__mul_operator && this_token.type!=__div_operator)
{
parse.push(this_token);
break;
}
temp.set_type(this_token.type);
temp.add_child(new_node);
}
return new_node;
}
abstract_syntax_tree balloon_parse::scalar()
{
abstract_syntax_tree new_node;
get_token();
switch(this_token.type)
{
case __func:parse.push(this_token);new_node=func_generate();break;
case __left_bracket:parse.push(this_token);new_node=array_generate();break;
case __left_brace:parse.push(this_token);new_node=hash_generate();break;
case __left_curve: case __left_curve:
case __nor_operator: case __nor_operator:
case __sub_operator: case __sub_operator:
case __number: case __number:
case __string: case __string:
case __id:parse.push(this_token);calculation();break; case __id:parse.push(this_token);new_node=calculation();break;
default: default:
++error; ++error;
std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar at this place."<<std::endl; std::cout<<">>[Parse-error] line "<<this_token.line<<": expect a scalar at this place."<<std::endl;
parse.push(this_token); parse.push(this_token);
break; break;
} }
return; return new_node;
} }
void balloon_parse::check_semi() void balloon_parse::check_semi()
@@ -546,6 +888,7 @@ void balloon_parse::check_semi()
void balloon_parse::parse_main() void balloon_parse::parse_main()
{ {
root.set_clear();
root.set_type(__root); root.set_type(__root);
error=0; error=0;
warning=0; warning=0;
@@ -555,7 +898,7 @@ void balloon_parse::parse_main()
get_token(); get_token();
switch(this_token.type) switch(this_token.type)
{ {
case __var:parse.push(this_token);definition();check_semi();break; case __var:parse.push(this_token);root.add_child(definition());check_semi();break;
case __left_curve: case __left_curve:
case __left_bracket: case __left_bracket:
case __left_brace: case __left_brace:
@@ -563,9 +906,12 @@ void balloon_parse::parse_main()
case __sub_operator: case __sub_operator:
case __number: case __number:
case __string: case __string:
case __id:parse.push(this_token);scalar();check_semi();break; case __id:parse.push(this_token);root.add_child(scalar());check_semi();break;
case __if:parse.push(this_token);break; case __if:parse.push(this_token);root.add_child(choose());break;
case __while:parse.push(this_token);break; case __for:
case __forindex:
case __foreach:
case __while:parse.push(this_token);root.add_child(loop());break;
case __semi:break; case __semi:break;
default: default:
++error; ++error;
+8
View File
@@ -51,10 +51,14 @@ enum parse_type
//basic elements //basic elements
__null_node, __null_node,
__block,
__array,
__hash,
__root, __root,
__loop, __loop,
__ifelse, __ifelse,
__function, __function,
__parameter,
__definition, __definition,
__assignment, __assignment,
__call_array, __call_array,
@@ -115,10 +119,14 @@ void print_detail_token(int type)
case __string: context="str";break; case __string: context="str";break;
case __null_node: context="null node";break; case __null_node: context="null node";break;
case __block: context="block";break;
case __array: context="array";break;
case __hash: context="hash";break;
case __root: context="root";break; case __root: context="root";break;
case __loop: context="loop";break; case __loop: context="loop";break;
case __ifelse: context="if-else";break; case __ifelse: context="if-else";break;
case __function: context="function";break; case __function: context="function";break;
case __parameter: context="parameter";break;
case __definition: context="definition";break; case __definition: context="definition";break;
case __assignment: context="assignment";break; case __assignment: context="assignment";break;
case __call_array: context="call array";break; case __call_array: context="call array";break;
+4
View File
@@ -67,6 +67,10 @@ int main()
{ {
pas.get_detail_token_stream(lex.get_detail_token()); pas.get_detail_token_stream(lex.get_detail_token());
pas.parse_main(); pas.parse_main();
if(!pas.get_error())
pas.print_generated_tree();
else
std::cout<<">>[Parse] error(s) found,stop."<<std::endl;
} }
else else
std::cout<<">>[Lexer] error(s) found,stop."<<std::endl; std::cout<<">>[Lexer] error(s) found,stop."<<std::endl;