20 个版本

0.3.0 2019年12月22日
0.2.13 2019年11月6日
0.2.12 2019年10月19日
0.1.5 2019年10月6日

编程语言 中排名 416

每月下载量 50

MIT 许可证

8MB
81K SLoC

tsar

Tsar 是一种动态类型、即时编译的编程语言。Tsar 靶向 Xasm 中间表示,可以编译成 Go语言或 Rust语言。因此,如果 Tsar 程序无法用 Go语言(主要目标语言)构建,则会使用 Rust 作为后备。

Rust Fallback

特性

  • 动态类型
  • Go语言和 Rust 外部函数接口
  • 包管理系统
  • 一等对象和函数编程
  • 美观的错误信息
  • Rust 启发式语法
  • 受 Python 启发式编程
tsar x.x.x
adam-mcdaniel <adam.mcdaniel17@gmail.com>
Compiler for the Tsar programming langauge

USAGE:
    tsar [SUBCOMMAND]

FLAGS:
    -h, --help       Prints help information
    -V, --version    Prints version information

SUBCOMMANDS:
    build    Build a Tsar package
    help     Prints this message or the help of the given subcommand(s)
    new      Create new Tsar package
    run      Run a Tsar package

安装

待办事项:为每个相应的操作系统制作文档

安装 Rust(可选安装 Go语言)

MacOS / Debian / Ubuntu

首先,安装 Rust

# For *nix only
# Installs Rust
curl --proto '=https' --tlsv1.2 -sSf https://sh.rustup.rs | sh

然后安装 git

# For debian based OS only
sudo apt install git

如果您想针对 golang(强烈推荐),请在此处安装它 这里

# For debian based OS only
sudo apt install golang-go

# For MacOS, use the golang link above.

Windows

请注意,Tsar 在 Windows 上的构建速度显著较慢。在编译/运行您的 tsar 包时,请预期额外的几秒钟时间。建议在 Linux 上使用 Tsar。

在开始之前,您必须安装 visual studiogit。没有这些您将无法编译!

请务必仔细阅读说明,并使用安装程序的默认值。

安装 Tsar

按照您相应操作系统的说明完成操作后,请在您的 shell 中运行以下命令。

cargo install -f tsar

安装完成后,您将能够创建一个 tsar 包!

入门

待办事项:这将成为未来的书籍/文档

首先,创建一个 tsar 包并对其进行测试。

# Where I will create my package
cd ~/Documents/tsar

# This will create a package named `test` under a folder with the same name
tsar new test
# Enter the folder
cd test

# Edit your program
nano src/bin.ts

# Compile your package
tsar build
# Your executable is in the `target` folder!

# Alternatively, you can `run` your package
tsar run

Hello World!

现在我们可以开始编程了!

语法

尽管Tsar的设计理念与Python相似,但其语法受到了Rust的启发。

Clock Example

如果您不小心犯了语法错误,Tsar会尝试帮助您纠正。

Error Message

注释

Tsar使用C和C++风格的注释。

// Im a comment!!
/*
    Im also a comment!
*/

println("Im not a comment!");

使用语句

Use语句允许您从导入的模块中导入对象。

Use语句必须仅放在文件顶部!您不能在代码的其他地方使用use语句,因为这会影响代码的整洁性。这可以使代码更易于阅读。

使用语句必须仅按名称导入,您不能像Python中那样使用*符号。

您可以这样从模块中导入一个对象。

use core::string::fmt;

您也可以导入多个对象。

use core::math::{sin, cos, tan};

标识符

标识符主要有两种类型:未限定的和限定名称。

未限定的名称就像abc123tsarihey_jude71这样的常规标识符。

限定名称使用::运算符。这个运算符让您可以访问模块内的名称。

如果我想从std模块中的time模块调用hour函数,我可以这样做。

println(std::time::hour());

赋值

Tsar中的赋值使用=运算符。变量在首次赋值时声明。

a = 5;
a = "String";
println(a);

循环和If语句

循环和If语句是Tsar中控制流程的结构。

如果语句可以是单枝或双枝,如下所示。

fn odd(n) => n % 2;

fn collatz(n) {
    if odd(n) { 3 * n + 1 }
    else { n / 2 }
}

if true {
    println(collatz(5));
}

循环或if语句不需要括号。

while循环会在测试表达式为假时执行。

n = 10
while n isnt 0 {
    println(n);
    n = n - 1;
}

println("loop finished");

for循环遍历列表中的每个索引和值。

use core::string::fmt;

for index, element in range(0, 10) {
    println("Index of element: " + fmt(index));
    println("Element itself: " + fmt(element));
}

在迭代时,对于未使用的索引或元素值,出于良好习惯使用_变量。

函数

在Tsar中,堆栈在不同作用域间是共享的。这意味着函数返回的值只是简单地推入堆栈以供以后检索。

要从函数返回一个值,只需在函数末尾留下要返回的表达式即可。

函数的最后一行不需要分号。

fn function_name(a, b) {
    result = a + b;
    result
}

只做一次计算的函数可以写成这样。

fn sum(array) => reduce(array, add, 0);

虽然这样写的函数确实需要分号。

匿名函数可以用以下语法表示。

|a, b| {
    result = a + b;
    result
};

此函数接受两个参数ab,并返回a + b

函数可以用与大多数其他语言相同的()运算符调用。

f = |a, b| { a + b };
fn increment(n) => n + 1;

println(f(4, 5));
println(increment(0));

对象

对象对于封装可变代码非常有用。为了保持代码整洁,Tsar摒弃了类继承。

对象的定义如下。

new方法用作对象的构造函数。new方法至少接受一个参数(当前实例的引用),并返回该实例。

您必须在new方法的末尾返回您的实例!!!

impl Point {
    fn new(self, x, y) {
        self.x = x;
        self.y = y;

        self
    }

    fn goto(self, x, y) {
        self.x = x;
        self.y = y;
    }
}

要实例化您的对象,请使用new函数。

p1 = new(Point, 5, 6);
println(p1);

对象属性可以通过与列表类似的操作符访问,例如使用 [] 操作符以及 . 操作符。

impl Example {
    fn new(self) {
        self.a = 5;
        self
    }
}

e = new(Example);
println(e["a"]);
println(e.a);

预定义库

在开始编程之前,你应该了解从 corestd 模块导入的可用预定义函数。

print

此函数打印对象而不换行。

print("test\n");

println

此函数打印对象并换行。

println("test");

list

以下段创建了一个包含3个元素的列表,[1, 2, 3]。创建列表的 [] 语法只是创建对 list 函数的调用的快捷方式。

n = 3
l = list(n, 1, 2, 3);
println(l);

len

此函数返回列表或字符串的长度。

println(len("testing"));
println(len([1, 2, 3]));

push

此函数返回一个新列表,其中包含附加到末尾的对象。

println(push([1], 2) is [1, 2]);

pop

此函数返回

  • 移除最后一个对象的列表
  • 被移除的对象
impl List {
    fn new(self) { self.items = []; self }
    fn push(self, item) {
        self.items = push(self.items, item);
    }

    fn pop(self) {
        self.items = pop(self.items);
    }
}

l = new(List);
l.push(5);
println(l.pop());

range

此函数返回从一数字到另一数字(不包括)的值列表。

println(range(0, 3))

reverse

此函数返回一个反转的列表。

println(reverse(range(0, 3)));

map

此函数使用一个函数将一个列表映射到另一个列表。

fn increment(n) => n + 1;

println(
    map([0, 0, 0, 0], increment)
);

filter

此函数用于过滤列表以获取接受值。它接受一个列表和一个函数。对于列表中的每个元素,如果 f(element) 为真,则项目将被放置在结果列表中。

以下将打印只包含奇数的列表。

fn odd(n) => (n % 2) is 1;

println(filter([1, 2, 3, 4, 5], odd));

reduce

此函数用于将列表缩减为原子值。Reduce 接受一个列表、一个用于缩减的函数(该函数本身接受两个参数)以及一个初始值。

fn sum(values) => reduce(values, add, 0);
fn factorial(n) => reduce(range(1, n+1), mul, 1);

println(sum([1, 2, 3]));
println(factorial(5));

new

此函数创建一个对象实例。

impl Point {
    fn new(self, x, y) {
        self.x = x;
        self.y = y;
        self
    }
}

p1 = new(Point, 1, 1);
println(p1);

依赖关系

~17MB
~388K SLoC