Add notes

This commit is contained in:
Valk Richard Li 2019-11-14 19:29:43 +08:00 committed by GitHub
parent 763af6e7aa
commit c421f726fa
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 177 additions and 78 deletions

View File

@ -4,8 +4,9 @@
int exit_type=0; int exit_type=0;
std::stack<var> ret_stack;// for function ret use std::stack<var> ret_stack; // for function ret use
std::list<var> parameter;// for function call use std::list<var> parameter; // for function call use
var abstract_syntax_tree::calculation() var abstract_syntax_tree::calculation()
{ {
@ -30,12 +31,23 @@ var abstract_syntax_tree::calculation()
} }
else if(this->type==__array) else if(this->type==__array)
{ {
temp=this->array_generation(); temp.set_type(__var_array);
if(!children.empty())
for(std::list<abstract_syntax_tree>::iterator i=children.begin();i!=children.end();++i)
temp.append_array(i->calculation());
return temp; return temp;
} }
else if(this->type==__hash) else if(this->type==__hash)
{ {
temp=this->hash_generation(); temp.set_type(__var_hash);
if(!children.empty())
for(std::list<abstract_syntax_tree>::iterator i=children.begin();i!=children.end();++i)
{
var t;
t=i->children.front().calculation();
t.set_name(i->name);
temp.append_hash(t);
}
return temp; return temp;
} }
else if(this->type==__function) else if(this->type==__function)
@ -477,31 +489,6 @@ var abstract_syntax_tree::call_identifier()
return temp; return temp;
} }
var abstract_syntax_tree::array_generation()
{
var new_var;
new_var.set_type(__var_array);
if(!children.empty())
for(std::list<abstract_syntax_tree>::iterator i=children.begin();i!=children.end();++i)
new_var.append_array(i->calculation());
return new_var;
}
var abstract_syntax_tree::hash_generation()
{
var new_var;
new_var.set_type(__var_hash);
if(!children.empty())
for(std::list<abstract_syntax_tree>::iterator i=children.begin();i!=children.end();++i)
{
var temp;
temp=i->children.front().calculation();
temp.set_name(i->name);
new_var.append_hash(temp);
}
return new_var;
}
var* abstract_syntax_tree::get_var_addr() var* abstract_syntax_tree::get_var_addr()
{ {
var* addr=&error_var; var* addr=&error_var;
@ -697,6 +684,8 @@ void abstract_syntax_tree::run_root()
} }
end_time=time(NULL); end_time=time(NULL);
std::cout<<"------------------------------------------------------------------------------"<<std::endl; std::cout<<"------------------------------------------------------------------------------"<<std::endl;
if(exit_type!=__process_exited_successfully)
alert_sound();
std::cout<<">>[Runtime] process exited after "<<end_time-beg_time<<" sec(s) with returned state \'"; std::cout<<">>[Runtime] process exited after "<<end_time-beg_time<<" sec(s) with returned state \'";
print_exit_type(exit_type); print_exit_type(exit_type);
std::cout<<"\'."<<std::endl; std::cout<<"\'."<<std::endl;

View File

@ -201,8 +201,6 @@ class abstract_syntax_tree
var calculation(); var calculation();
bool condition_check(); bool condition_check();
var call_identifier(); var call_identifier();
var array_generation();
var hash_generation();
var* get_var_addr(); var* get_var_addr();
var assignment(); var assignment();
void run_root(); void run_root();

View File

@ -1,6 +1,16 @@
#ifndef __BALLOON_H__ #ifndef __BALLOON_H__
#define __BALLOON_H__ #define __BALLOON_H__
/*
Balloon language made by ValKmjolnir
place: NUAA QQ: 896693328 e-mail: 896693328@qq.com
Balloon is a real subset of Nasal language
Nasal language is created for FlightGear
Nasal language seems like ECMAscript
So you may find some similarities between nas & js
*/
#include <iostream> #include <iostream>
#include <cstdlib> #include <cstdlib>
#include <cstring> #include <cstring>
@ -10,13 +20,34 @@
#include <stack> #include <stack>
#include <ctime> #include <ctime>
#include "balloon_type.h" void alert_sound()
#include "abstract_syntax_tree.h" {
#include "balloon_var.h" printf("\a");
#include "balloon_lexer.h" return;
#include "balloon_parse.h" }
#include "balloon_scope.h"
#include "abstract_syntax_tree.cpp"
#include "balloon_type.h" // place some enums
#include "abstract_syntax_tree.h" // ast
#include "balloon_var.h" // var
/* global varia in balloon_var.h :
var error_var; // give an error_var to get
*/
#include "balloon_lexer.h" // lexer
/* global varia in balloon_lexer.h :
struct token; // used to get token from resource codes
std::string reserve_word[15]; // place many reserve words
int is_reserve_word(std::string str); // check the string is a reserve word or not and return the number of reserve word
bool check_number(std::string str); // check the string can be processed to number or not
*/
#include "balloon_parse.h" // parser
#include "balloon_scope.h" // place to store vars
/* global varia in balloon_scope.h :
balloon_scope scope; // make a place to vars
*/
#include "abstract_syntax_tree.cpp" // runtime
/* global varia in abstract_syntax_tree.cpp :
int exit_type; // record the state of runtime
std::stack<var> ret_stack; // for function ret use
std::list<var> parameter; // for function call use
*/
#endif #endif

View File

@ -1,12 +1,17 @@
#ifndef __BALLOON_LEXER_H__ #ifndef __BALLOON_LEXER_H__
#define __BALLOON_LEXER_H__ #define __BALLOON_LEXER_H__
/*
reserve words are those below
and they are also the reserve words of nasal
*/
std::string reserve_word[15]= std::string reserve_word[15]=
{ {
"for","foreach","forindex","while", "for","foreach","forindex","while",
"var","func","break","continue","return", "var","func","break","continue","return",
"if","else","elsif","nil","and","or" "if","else","elsif","nil","and","or"
}; };
int is_reserve_word(std::string str) int is_reserve_word(std::string str)
{ {
for(int i=0;i<15;++i) for(int i=0;i<15;++i)
@ -14,6 +19,10 @@ int is_reserve_word(std::string str)
return __reserve_word; return __reserve_word;
return __token_identifier; return __token_identifier;
} }
/*
check if the generated string can be put to number
*/
bool check_number(std::string str) bool check_number(std::string str)
{ {
if(str.length()==1) if(str.length()==1)
@ -63,7 +72,12 @@ bool check_number(std::string str)
return false; return false;
} }
/*
use std::list<char> to store resource codes
and if you continue adding files
the codes will be added behind files that have
been added in before
*/
class resource_file class resource_file
{ {
private: private:
@ -108,6 +122,8 @@ class resource_file
{ {
if(32<=*i && *i<128 || *i=='\n') if(32<=*i && *i<128 || *i=='\n')
std::cout<<*i; std::cout<<*i;
else if(*i=='\t')
std::cout<<" ";
if(*i=='\n') if(*i=='\n')
{ {
++line; ++line;
@ -125,7 +141,15 @@ struct token
int type; int type;
std::string str; std::string str;
}; };
/*
lexer can recognize:
number: 100(int) 0.001(double) 0xdeadbeef(hex) 0o1701(oct)
string: "str" 'str'
identifier
reserve word
normal identifier: ID and id is different
operator
*/
class balloon_lexer class balloon_lexer
{ {
private: private:

View File

@ -81,26 +81,58 @@ class balloon_parse
root.run_root(); root.run_root();
return; return;
} }
/*
ret: return expression
choose: if-else expression
loop: while/for/forindex/foreach expression
definition
assignment
block: set of expressions
generate:
array
hash
number
string
function
block
scalar:
calculation:
calculation_or:
calculation_and:
calculation_cmp:
calculation_additive:
calculation_multive:
call_identifier
unary expression
->generate
semi: check if the statements is ended with semi
parse_main: main process
*/
abstract_syntax_tree ret(); abstract_syntax_tree ret();
abstract_syntax_tree choose(); abstract_syntax_tree choose();
abstract_syntax_tree loop(); abstract_syntax_tree loop();
abstract_syntax_tree definition(); abstract_syntax_tree definition();
abstract_syntax_tree assignment(); abstract_syntax_tree assignment();
abstract_syntax_tree block();
abstract_syntax_tree array_generate(); abstract_syntax_tree array_generate();
abstract_syntax_tree hash_generate(); abstract_syntax_tree hash_generate();
abstract_syntax_tree func_generate();
abstract_syntax_tree check_number(); abstract_syntax_tree check_number();
abstract_syntax_tree check_string(); abstract_syntax_tree check_string();
abstract_syntax_tree check_unary();
abstract_syntax_tree block(); abstract_syntax_tree scalar();
abstract_syntax_tree func_generate();
abstract_syntax_tree call_identifier(); abstract_syntax_tree call_identifier();
abstract_syntax_tree check_unary();
abstract_syntax_tree calculation(); abstract_syntax_tree calculation();
abstract_syntax_tree calculation_or(); abstract_syntax_tree calculation_or();
abstract_syntax_tree calculation_and(); abstract_syntax_tree calculation_and();
abstract_syntax_tree calculation_cmp(); abstract_syntax_tree calculation_cmp();
abstract_syntax_tree calculation_additive(); abstract_syntax_tree calculation_additive();
abstract_syntax_tree calculation_multive(); abstract_syntax_tree calculation_multive();
abstract_syntax_tree scalar();
void check_semi(); void check_semi();
void parse_main(); void parse_main();
}; };
@ -489,7 +521,7 @@ abstract_syntax_tree balloon_parse::block()
{ {
abstract_syntax_tree new_node; abstract_syntax_tree new_node;
abstract_syntax_tree temp; abstract_syntax_tree temp;
new_node.set_type(__block); new_node.set_type(__normal_block);
get_token(); get_token();
if(this_token.type!=__left_brace) if(this_token.type!=__left_brace)
{ {

View File

@ -6,6 +6,14 @@ class balloon_scope
private: private:
std::list<var> global; std::list<var> global;
std::list<std::list<std::list<var> > > scope_list; std::list<std::list<std::list<var> > > scope_list;
/*
example:
std::list<var> global // global scope
std::list<std::list<std::list<var> > > // total scope
-> std::list<std::list<var> > // block scope
->std::list<var> // local scope
-> var -> var -> var -> var
*/
public: public:
void set_clear() void set_clear()
{ {

View File

@ -51,7 +51,7 @@ enum parse_type
//basic elements //basic elements
__null_node, __null_node,
__block, __normal_block,
__array, __array,
__hash, __hash,
__root, __root,
@ -65,6 +65,7 @@ enum parse_type
__call_hash, __call_hash,
__call_function __call_function
}; };
void print_detail_token(int type) void print_detail_token(int type)
{ {
std::string context=""; std::string context="";
@ -119,7 +120,7 @@ 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 __normal_block: context="block";break;
case __array: context="array";break; case __array: context="array";break;
case __hash: context="hash";break; case __hash: context="hash";break;
case __root: context="root";break; case __root: context="root";break;
@ -138,6 +139,34 @@ void print_detail_token(int type)
return; return;
} }
enum var_type
{
__null_type,
__var_number,
__var_string,
__var_array,
__var_hash,
__var_function
};
void print_scalar(int type)
{
std::string str="";
switch(type)
{
case __null_type: str="null";break;
case __var_number: str="number";break;
case __var_string: str="string";break;
case __var_array: str="array";break;
case __var_hash: str="hash";break;
case __var_function:str="function";break;
default: str="unknown";break;
}
std::cout<<str;
return;
}
enum runtime_error_type enum runtime_error_type
{ {
__process_exited_successfully, __process_exited_successfully,

View File

@ -1,33 +1,6 @@
#ifndef __BALLOON_VAR_H__ #ifndef __BALLOON_VAR_H__
#define __BALLOON_VAR_H__ #define __BALLOON_VAR_H__
enum var_type
{
__null_type,
__var_number,
__var_string,
__var_array,
__var_hash,
__var_function
};
void print_scalar(int type)
{
std::string str="";
switch(type)
{
case __null_type: str="null";break;
case __var_number: str="number";break;
case __var_string: str="string";break;
case __var_array: str="array";break;
case __var_hash: str="hash";break;
case __var_function:str="function";break;
default: str="unknown";break;
}
std::cout<<str;
return;
}
class var class var
{ {
private: private:

View File

@ -29,9 +29,9 @@ int main()
else if(command=="cls") else if(command=="cls")
{ {
system("cls"); system("cls");
//windows system("cls"); // Windows system("cls");
//linux system("clear"); // Linux system("clear");
//macOS system("clear"); // MacOS system("clear");
} }
else if(command=="rs") else if(command=="rs")
prog.print_file(); prog.print_file();
@ -59,7 +59,10 @@ int main()
pas.parse_main(); pas.parse_main();
} }
else else
{
alert_sound();
std::cout<<">>[Lexer] error(s) found,stop."<<std::endl; std::cout<<">>[Lexer] error(s) found,stop."<<std::endl;
}
} }
else if(command=="ast") else if(command=="ast")
{ {
@ -72,10 +75,16 @@ int main()
if(!pas.get_error()) if(!pas.get_error())
pas.print_generated_tree(); pas.print_generated_tree();
else else
{
alert_sound();
std::cout<<">>[Parse] error(s) found,stop."<<std::endl; std::cout<<">>[Parse] error(s) found,stop."<<std::endl;
}
} }
else else
{
alert_sound();
std::cout<<">>[Lexer] error(s) found,stop."<<std::endl; std::cout<<">>[Lexer] error(s) found,stop."<<std::endl;
}
} }
else if(command=="run") else if(command=="run")
{ {
@ -88,10 +97,16 @@ int main()
if(!pas.get_error()) if(!pas.get_error())
pas.run_tree(); pas.run_tree();
else else
{
alert_sound();
std::cout<<">>[Parse] error(s) found,stop."<<std::endl; std::cout<<">>[Parse] error(s) found,stop."<<std::endl;
}
} }
else else
{
alert_sound();
std::cout<<">>[Lexer] error(s) found,stop."<<std::endl; std::cout<<">>[Lexer] error(s) found,stop."<<std::endl;
}
} }
else else
prog.input_file(command); prog.input_file(command);