update readme:difference between this and andy's interpreter
This commit is contained in:
parent
aa797142d1
commit
df634cb1b2
53
README.md
53
README.md
|
@ -774,3 +774,56 @@ nasal_val* builtin_keys(std::vector<nasal_val*>& local_scope,nasal_gc& gc)
|
|||
return ret_addr;
|
||||
}
|
||||
```
|
||||
|
||||
## Difference Between Andy's Nasal Interpreter and This Interpreter
|
||||
|
||||
This interpreter uses more strict syntax to make sure it is easier for you to program and debug.
|
||||
|
||||
In Andy's interpreter:
|
||||
|
||||
```javascript
|
||||
foreach(i;[0,1,2,3])
|
||||
print(i)
|
||||
```
|
||||
|
||||
This program can run normally with output 0 1 2 3.
|
||||
But take a look at the iterator 'i',this symbol is defined in foreach without using keyword 'var'.
|
||||
I think this design will make programmers filling confused.
|
||||
This is ambiguous that programmers maybe difficult to find the 'i' is defined here.
|
||||
Without 'var',programmers may think this 'i' is defined anywhere else.
|
||||
|
||||
So in this new interpreter i use a more strict syntax to force users to use 'var' to define iterator of forindex and foreach.
|
||||
If you forget to add the keyword 'var', and you haven't defined this symbol before, you will get this:
|
||||
|
||||
```javascript
|
||||
>> [code] line 1: undefined symbol "i".
|
||||
>> [codegen] in <"test.nas">: error(s) occurred,stop.
|
||||
```
|
||||
|
||||
Also there's another difference.
|
||||
In Andy's interpreter:
|
||||
|
||||
```javascript
|
||||
var a=func {print(b);}
|
||||
var b=1;
|
||||
a();
|
||||
```
|
||||
|
||||
This program runs normally with output 1.
|
||||
But in this new interpreter, it will get:
|
||||
|
||||
```javascript
|
||||
>> [code] line 1: undefined symbol "b".
|
||||
>> [codegen] in <"test.nas">: error(s) occurred,stop.
|
||||
```
|
||||
|
||||
This difference is caused by different kinds of ways of lexical analysis.
|
||||
In most script language interpreters, they use dynamic analysis to check if this symbol is defined yet.
|
||||
However, this kind of analysis is at the cost of lower efficiency.
|
||||
To make sure the interpreter runs at higher efficiency, i choose static analysis to manage the memory space of each symbol.
|
||||
By this way, runtime will never need to check if a symbol exists or not.
|
||||
But this causes a difference.
|
||||
You will get an error of 'undefined symbol', instead of nothing happening in most script language interpreters.
|
||||
|
||||
This change is __controversial__ among FGPRC's members.
|
||||
So maybe in the future i will use dynamic analysis again to cater to the habits of senior programmers.
|
||||
|
|
23
main.cpp
23
main.cpp
|
@ -18,20 +18,23 @@ void help_cmd()
|
|||
#ifdef _WIN32
|
||||
<<"use command \'chcp 65001\' if want to use unicode.\n"
|
||||
#endif
|
||||
<<"nasal | use interactive interpreter.\n"
|
||||
<<"nasal -h, --help | get help.\n"
|
||||
<<"nasal -v, --version | get version of nasal interpreter.\n"
|
||||
<<"nasal filename | execute script file.\n";
|
||||
<<"nasal [option]|[file]\n"
|
||||
<<" input 0 argument to use the interactive interpreter.\n"
|
||||
<<"option:\n"
|
||||
<<" -h, --help | get help.\n"
|
||||
<<" -v, --version | get version of nasal interpreter.\n"
|
||||
<<"file:\n"
|
||||
<<" input file name to execute script file.\n";
|
||||
return;
|
||||
}
|
||||
void info()
|
||||
{
|
||||
std::cout
|
||||
<<">> Thanks to https://github.com/andyross/nasal\n"
|
||||
<<">> Code: https://github.com/ValKmjolnir/Nasal-Interpreter\n"
|
||||
<<">> Code: https://gitee.com/valkmjolnir/Nasal-Interpreter\n"
|
||||
<<">> Info: http://wiki.flightgear.org/Nasal_scripting_language\n"
|
||||
<<">> Input \"help\" to get help .\n";
|
||||
<<">> thanks to https://github.com/andyross/nasal\n"
|
||||
<<">> code: https://github.com/ValKmjolnir/Nasal-Interpreter\n"
|
||||
<<">> code: https://gitee.com/valkmjolnir/Nasal-Interpreter\n"
|
||||
<<">> info: http://wiki.flightgear.org/Nasal_scripting_language\n"
|
||||
<<">> input \"help\" to get help .\n";
|
||||
return;
|
||||
}
|
||||
void logo()
|
||||
|
@ -42,7 +45,7 @@ void logo()
|
|||
<<" / \\/ / _` / __|/ _` | | \n"
|
||||
<<" / /\\ / (_| \\__ \\ (_| | | \n"
|
||||
<<" \\_\\ \\/ \\__,_|___/\\__,_|_|\n"
|
||||
<<" Nasal interpreter ver 7.0 \n";
|
||||
<<" nasal interpreter ver 7.0 \n";
|
||||
return;
|
||||
}
|
||||
void die(const char* stage,std::string& filename)
|
||||
|
|
10
nasal_ast.h
10
nasal_ast.h
|
@ -80,8 +80,8 @@ nasal_ast::nasal_ast(const nasal_ast& tmp)
|
|||
{
|
||||
line=tmp.line;
|
||||
type=tmp.type;
|
||||
str =tmp.str;
|
||||
num =tmp.num;
|
||||
str =tmp.str;
|
||||
children=tmp.children;
|
||||
return;
|
||||
}
|
||||
|
@ -90,8 +90,8 @@ nasal_ast::nasal_ast(nasal_ast&& tmp)
|
|||
{
|
||||
line=tmp.line;
|
||||
type=tmp.type;
|
||||
str.swap(tmp.str);
|
||||
num =tmp.num;
|
||||
str.swap(tmp.str);
|
||||
children.swap(tmp.children);
|
||||
return;
|
||||
}
|
||||
|
@ -100,8 +100,8 @@ nasal_ast& nasal_ast::operator=(const nasal_ast& tmp)
|
|||
{
|
||||
line=tmp.line;
|
||||
type=tmp.type;
|
||||
str=tmp.str;
|
||||
num=tmp.num;
|
||||
str=tmp.str;
|
||||
children=tmp.children;
|
||||
return *this;
|
||||
}
|
||||
|
@ -110,8 +110,8 @@ nasal_ast& nasal_ast::operator=(nasal_ast&& tmp)
|
|||
{
|
||||
line=tmp.line;
|
||||
type=tmp.type;
|
||||
str.swap(tmp.str);
|
||||
num=tmp.num;
|
||||
str.swap(tmp.str);
|
||||
children.swap(tmp.children);
|
||||
return *this;
|
||||
}
|
||||
|
@ -119,8 +119,8 @@ nasal_ast& nasal_ast::operator=(nasal_ast&& tmp)
|
|||
void nasal_ast::clear()
|
||||
{
|
||||
line=0;
|
||||
str="";
|
||||
num=0;
|
||||
str="";
|
||||
type=ast_null;
|
||||
children.clear();
|
||||
return;
|
||||
|
|
Loading…
Reference in New Issue