Since C++ is Cplusplus, I used Cploxplox and Cxx :)
A Lox Interpreter implemented using Modern C++
This code is based on C++17, so you'll need g++-8 or higher version to compile.
For Windows User, I suggest using TDM-GCC. Just be aware that you'll have to manually rename "mingw32-make" to "make".
- Run
make
under the root folder - The executable
cploxplox
will be generated inoutput
folder make clean
can delete all .o filesmake clean
can delete the executable as well
To see full Grammar, please goto grammar.md
lox > var a = 1;
lox > var b;
You have to declare a variable before using it. Use var
to declare, with or without an init value.
lox > func div(a,b=1) {
... return a/b;
... }
Unlike the original Lox, I used func
as the keyword for function. You can declare a function with name, or a lambda expression without name. See expression for Lambda.
lox > class A {
... init() {
... this.name = "A";
... }
...
... hi() {
... print(this.name); // you have to use "this" for class-member
... }
... }
...
lox > class B > A {
... hi() {
... super.hi();
... print("B");
... }
... }
...
lox > var b = B();
lox > b.hi();
"A"
"B"
I used >
instead to represent inheritance, so be careful when running original lox code.
Block is the representation of a scope, each section surrounded by {}
will create a new Scope, and Lox is a Lexical Scoping language.
In most cases, Block is the accessory of other statement like for-loop
, but you could also use it alone:
lox > var a = "global";
... {
... func showA() {
... print(a);
... }
...
... showA();
... var a = "block";
... showA();
... print(a);
... }
"global"
"global"
"block"
This example shows you what is Lexical Scoping.
Lox only have if and else, and it's enough.
lox > func Range(age) {
... if (age < 18) {
... return "Teen";
... }
... else if (age < 35) {
... return "Programmer";
... }
... else {
... return "Retired";
... }
... }
...
lox > Range(16);
...
Teen
lox > Range(19);
...
Programmer
lox > Range(87);
...
Retired
Lox is not Python, you can't leave out the "()"
We have while and for loop, they all follow the syntax of C++.
lox > for(var i = 0; i < 3; i+=1){
... print(i);
... }
...
0
1
2
lox > var i = 0;
lox > while(i < 3){
... print(i++);
... }
...
0
1
2
As you can see,cploxplox support ++、--、+=、-=、*=、/=
break/continue can only be used inside loop statement.
lox > for(var i = 0; i < 10; i++){
... if(i > 5) break;
... if(i == 3) continue;
... print(i);
... }
...
0
1
2
4
5
You can return nothing, e.g. return;
, or return a value. Return can only be used inside a function.
Note: you can't return any value except nil in a class init function.
In the latest update, I introduced import
. It's similar to Python or TypeScript, you can import global functions, class, and variables from another lox script.
lox > import { add as a, sub as s } from "math.lox"
lox > a(1,2);
3
// or
lox > import { * } from "math"
lox > add(1,2);
3
Note:
- After
from
should be a filepath. If it's an absolute path, then the Interpreter will check if the file exists. Otherwise, the Interpreter will search the Environment for "LOXLIB", and go through each folder to find the script. If you haven't define "LOXLIB", then it will just look for the script under current running folder.- The filepath could leave out the extension, as shown in the example. The Interpreter will automatically add suffix ".lox".
Expression is mainly for all sort of arithmetic computation
- You can assign value to a declared variable.
- Or add new field to a Instance.
- Reassign list element.
lox > var a = 1;
lox > a += 10;
11
lox > class Person{}
lox > var me = Person();
lox > me.name = "Dave"
lox > list = [1,2,3];
lox > list[0] = "Hello";
When declaring function, if there is no name after keyword func
, then it will be a lambda function.
lox > func (a,b){return a+b;}(1,2);
3
Lambda is an expression,so it will return a value. You can assign it to a variable, pass it to another function, all sorts of things.
Go see scripts/doc/Built_in_Expansion_Guide.md
PS: May need update.
$ ./cploxplox -h
Welcome to cploxplox!
Usage: ./cploxplox [options...]
Options:
-f,--file : Execute Lox script from given file_path [default: none]
-i : A flag to toggle interactive mode [implicit: "true", default: false]
-v,--verbose : A flag to toggle verbose [implicit: "true", default: false]
-D,--Debug : A flag to toggle debug mode [implicit: "true", default: false]
-h,--help : print help [implicit: "true", default: false]
By default, cploxplox will run in REPL mode.
See Argparse,for further extension.
munificent | TobiPristupin | chanryu |
---|---|---|