语言特性概览

与 JS 比较

分号

JavaScriptReScript
被 linter/formatter 强制要求不需要分号!

注释

JavaScriptReScript
// 行注释相同
/* 块注释 */相同
/** 文档注释 *//** 类型/值之前的注释 */
/*** 独立的文档注释 */

变量

JavaScriptReScript
const x = 5;let x = 5
var x = y;无对应(谢天谢地)
let x = 5; x = x + 1;let x = ref(5); x := x.contents + 1

字符串和字符

JavaScriptReScript
"Hello world!"相同
'Hello world!'字符串必须使用 "
"hello " + "world""hello " ++ "world"
`hello ${message}`相同

布尔值

JavaScriptReScript
true, false相同
!true相同
||, &&, <=, >=, <, >相同
a === b, a !== b相同
没有深比较(递归比较)a == b, a != b
a == b相等判断没有隐式转换(谢天谢地)

数字

JavaScriptReScript
3相同 *
3.1415相同
3 + 4相同
3.0 + 4.53.0 +. 4.5
5 % 3mod(5, 3)

* JS 没有区分整数和浮点数。

对象/记录(Record)

JavaScriptReScript
没有类型type point = {x: int, mutable y: int}
{x: 30, y: 20}相同
point.x相同
point.y = 30;相同
{...point, x: 30}相同

数组

JavaScriptReScript
[1, 2, 3]相同
myArray[1] = 10相同
[1, "Bob", true](1, "Bob", true) *

* JS 中的异构(heterogenous)数组对我们来说是不允许的,使用元组(tuple)代替。

空值

JavaScriptReScript
null, undefinedNone *

* 同样,这里只是精神上的等价物;我们没有 null,也没有 null bug!但我们确实有一个 option 类型,当你真正需要 null 时可以使用这个类型。

函数

JavaScriptReScript
arg => retVal相同
function named(arg) {...}let named = (arg) => {...}
const f = function(arg) {...}let f = (arg) => {...}
add(4, add(5, 6))相同

代码块

JavaScriptReScript
const myFun = (x, y) => { const doubleX = x + x; const doubleY = y + y; return doubleX + doubleY };
let myFun = (x, y) => { let doubleX = x + x let doubleY = y + y doubleX + doubleY }

条件表达式

JavaScriptReScript
if (a) {b} else {c}if a {b} else {c} *
a ? b : c相同
switch拥有强大模式匹配功能!switch

* 我们的条件式总是表达式!你可以这样写:let result = if a {"hello"} else {"bye"}

解构

JavaScriptReScript
const {a, b} = datalet {a, b} = data
const [a, b] = datalet [a, b] = data *
const {a: aa, b: bb} = datalet {a: aa, b: bb} = data

* 给出良好的编译器警告,数据长度可能不为 2。

循环

JavaScriptReScript
for (let i = 0; i <= 10; i++) {...}for i in 0 to 10 {...}
for (let i = 10; i >= 0; i--) {...}for i in 10 downto 0 {...}
while (true) {...}while true {...}

JSX

JavaScriptReScript
<Comp message="hi" onClick={handler} />相同
<Comp message={message} /><Comp message /> *
<input checked /><input checked=true />
没有子节点展开<Comp>...children</Comp>

* 参数双关(punning)!

异常

JavaScriptReScript
throw new SomeError(...)raise(SomeError(...))
try {a} catch (Err) {...} finally {...}try a catch { | Err => ...} *

* 没有 finally。

代码块

{} 限定的块的隐式返回最后一个表达式(函数体也是这样)。在 JavaScript 中,这只能通过一个立即调用函数表达式(IIFE, Immediately Invoked Funtion Expression)来模拟(利用函数作用域)。

JavaScriptReScript
let result = (function() { const x = 23; const y = 34; return x + y; })();
let result = { let x = 23 let y = 34 x + y }

普通特性的 JS 输出

特性例子JavaScript 输出
字符串"Hello""Hello"
字符串插值`Hello ${message}`"Hello " + message
字符(不推荐)'x'120 (字符码)
整数23, -2323, -23
浮点数23.0, -23.023.0, -23.0
整数加法23 + 123 + 1
浮点加法23.0 +. 1.023.0 + 1.0
整数除法/乘法2 / 23 * 12 / 23 * 1
浮点除法/乘法2.0 /. 23.0 *. 1.02.0 / 23.0 * 1.0
浮点幂运算2.0 ** 3.0Math.pow(2.0, 3.0)
字符串拼接"Hello " ++ "World""Hello " + "World"
比较>, <, >=, <=>, <, >=, <=
布尔运算!, &&, ||!, &&, ||
浅等价和深等价===, =====, ==
列表(不推荐)list{1, 2, 3}{hd: 1, tl: {hd: 2, tl: {hd: 3, tl: 0}}}
列表头部拼接list{a1, a2, ...oldList}{hd: a1, tl: {hd: a2, tl: theRest}}
数组[1, 2, 3][1, 2, 3]
记录type t = {b: int}; let a = {b: 10}var a = {b: 10}
多行注释/* Comment here */无输出
单行注释// Comment here无输出

请注意,这是一个整理过的对照表;有几个例子的 JavaScript 输出与实际略有不同。