learn lua from javascript, part 1: An introduction to Lua

https://www.oreilly.com/learning/learn-lua-from-javascript-part-1-an-introduction-to-lua

learn lua from javascript, part 1: An introduction to Lua

学习 Lua 对于了解 Javascript 的人来说就是小菜一碟,Tyler Neylon 写了三篇文章来解释其中的原因,这是其中的第一篇。

这是通过 Javascript 来学习 Lua 系列文章的第一篇,一共有三篇,第二篇和第三篇。
登陆 Tyler 的免费的网络广播频道收听 Lua 能做什么?

Lua 是一门优雅的,可移植的,高效的并且异常灵活的语言。所有能够编译 C 语言的操作系统都能运行 Lua,这是一些跨平台的框架,比如 Corona SDK 和 Love game engine,选择 Lua 的原因。Lua 的运行速度很快,足够用来开发游戏——愤怒的小鸟的最初是用 Lua 编写的。 Lua 能和其他的语言很好的融合在一起,它作为脚本语言,在 Adobe lightroom 项目中有出色的表现。我认为 Lua 的设计很优美,用起来也非常的舒服。

对于已经了解 Javascript 的人而言,学习 Lua 是非常简单的,因为Lua 和 Javascript 有很多的共同点。在学习的过程中,我们可以通过这些共同点很快的熟悉 Lua,但需要注意两者间一些关键性的不同的地方。

通过 Javascript 的相关知识学习 Lua 的系列总共三篇,这是其中的第一篇。这篇文章中包含一些基础概念:安装 Lua,变量,数据类型,操作符和表达式。第二篇将会涉及流程控制和数据结构,第三篇讲解对象相关的一些知识。

文章中出现的 Javascript 代码大多都遵循 2009 年制定的 EACMScript 5 标准,也就是 ES5 标准。现在最新的 Javascript 标准的是 ES6 或者称为 ES2015。我会用到一些 ES6 的语法,并指出这是 ES6 的特性,这样读者就能知道这段 Javascript 代码遵循的标准。不过读者并不需要了解 ES6,我也不会对用到的 ES6 特性进行解释。

运行 Lua

官方安装指南传送门
如果在 Mac 上安装了 homebrew,运行 brew install lua。ubuntu 的话,运行 sudo apt-get install lua5.2,如果从源码编译安装可以安装最新的版本的 Lua。在 windows 上请使用 LuaDist 安装。

在 Max OSX 和 Linux 上通过编译源码的方式安装 Lua 很简单,执行下面的 shell 命令。如果是 Max OS X,把最后一行的 linux 替换为 macosx 。

curl -R -O http://www.lua.org/ftp/lua-5.3.3.tar.gz
tar zxf lua-5.3.3.tar.gz
cd lua-5.3.3
make linux test  # Mac 的话把 linux 替换为 macosx.

安装完成后,就可以使用 lua 命令了,运行 lua 应该看到以下输出。

$ lua
Lua 5.3.3  Copyright (C) 1994-2016 Lua.org, PUC-Rio
> 

任意一个文本编辑器都能用来写 Lua 脚本,写一段代码保存为 my_file.lua,执行 Lua 脚本类似 node.js 执行 Javascript 脚本,使用命令就好了。

lua my_file.lua

注释,空格和分号

Lua 中的多行注释的以 --[[ 开始,以 ]] 结尾。 如果 -- 之后没有 [[,那么这行是一个单行注释。例如:

print('Why, hello!')  -- print 方法输出一段字符串
--[[ 这里是一个
     多行注释!]]

Lua 会忽略缩进。一般的空格也会被忽略,但是会保留字符串的空格和单行注释后面的空白行。行尾的分号可写可不写,一般而言不用写。

变量和作用域

和 Javascript 一样, Lua 的变量是动态类型的,也使用垃圾回收器管理内存。多数的 Lua 变量类型都能在 Javascript 中找对应的类型。

Javascript 变量类型 Lua 变量类型 Lua 变量例子
boolean boolean true or false
null or undefined nil nil
number number 3.141
string string 'hi' or "there"
object or array table {a=1, [2]=false}
function function function() return 42 end
symbol(ES6) unique tables 'hi' or "there"

It's handy to classify boolean values in term of falsiness; a value is called falsy when it evaluates to false to a boolean context; Lua 中仅有的假值是 nil 和 false。类似地在 Javascript 中,0''undefined 都是假值。

Lua 的 numbers 类型,由于历史原因,使用了浮点数来表示——就像 Javascript 的 numbers。从 Lua 5.3 开始,Lua 增加了对整数类型的支持,increasing the range of integral values that can be represented exactly.

直观的来看,如果 Lua 的 number 类型变量被初始化为整数,它被当作一个整数,并且会一直保留整数形式直到遇到可将它变为非整数的操作,比如除法。下面的代码展示了 Lua 如何处计算数学表达式——有些运算得到整数,有些得到浮点数。

-- Lua
n = 100
print(n)      --> 100;   使用整数形式存储
print(n * 2)  --> 200;  运算结果是整数
print(n / 2)  -->  50.0; 运算结果是浮点数

类似 Javascript 中的 objects,Lua 的 table 类型是一个全能的数据结构。
table 可以被用做哈希表或者是数组。不过 Javascript 中 object 的 keys 只能是字符类型,Lua table 的 keys 可以是任何的非 nil 值。在 Lua 中 只有两个 table 是同一个对象时才会相等,而不是它们拥有相同的内容。

-- Lua
myTable = {}
print(myTable == myTable)  --> true
print(myTable == {})       --> false

Lua 中 function 是一等公民——可以创建匿名函数,把函数赋值给变量,也可以把函数当作另一个函数的参数或者返回值。如果在函数中引用了定义在该函数作用域之外的自由变量,将隐式地形成一个闭包(译者注:和 Javascript 中的闭包很类似)。同时 Lua 中的函数支持高效的尾递归,也就是在函数的结尾调用另一个函数,调用栈不会增加。

Lua 中还有两个类型 userdata 和 thread。userdata 是使用 Lua 的 C 语言 API 调用 C 语言生成的对象。userdata 就像一个拥有私有数据的 table,也可以自定义它的行为。 Lua 的 thread 是一个 coroutine,允许函数使用 yield 一些值并保持自身的栈和内部状态。

作用域和可变性

Lua 中变量的作用域默认是全局作用域。Lua 的 local 关键字有点像 Javascript 中的 var,只不过 Lua 中没有声明提升。也就是说,Lua 中的 local 和 ES6 中的 let 一样,都是块级作用域。

-- Lua
phi         = 1.618034  -- `phi` 是全局变量。
local gamma = 0.577216  -- `gamma` 只在当前的块作用域下可见。

Lua 中没有常量或者私有变量。不过可以像 Javascript 中一样,使用闭包来模拟私有变量。创建一个函数,在函数中引用定义在函数之外的变量,这就使得这些变量在函数之外不可见,达到类似私有变量的效果。 Lua 的函数相关内容将在下一篇文章中涉及。

操作符和表达式

Lua 和 Javascript 中的数学运算,像是加法和乘法,基本上是一样的。两者都提供了获取余数的操作,不同的是: Javascript 中的 在左侧操作数是负数时会返回负值,而 Lua 中的 总是返回非负值。Lua 中可以使用 ^ 进行指数操作。

-- Lua
print(2 ^ 10)  --> 1024.0
print(-2 % 7)  --> 5

Javascript 不支持操作符重载,但是 Lua 支持。Lua 通过一种称为 metamethods(修改元数据) 特殊函数实现的重载,这部分内容将会在最后一篇文章中解释。Javascript 有一个三元操作符,但 Lua 中并没有,不过在 Lua 中能实现类似的效果,这需要借助 Lua 中的短路操作符 or 和 and。

-- Lua

-- Lua 中模拟三元操作符.
local x = myBoolean and valueOnTrue or valueOnFalse

-- 例子:找到 a 和 b 的中的最大值.
local maxNum = (a > b) and a or b

-- 类似 Javascript 中的以下代码
-- var maxNum = (a > b) ? a : b;

这个实现很有效除非 valueOnTrue 是假值。大部分情况下都不会有问题因为 Lua 的数字,字符和表不会被当作假值。

比较

在 Javascript 中被广泛认同的的一个最佳实践是使用 == 而不是 ==,因为 Javascript 中的 == 引发令人疑惑的隐式的类型转换。对于 ===, Javascript 只有当比较的值有相同的类型的时候才会返回 true

Lua 只有 == 一种比较操作符,和 Javascript 中的 === 一样要求类型相同。以下的例子使用了 Lua 中的内置函数 tonumber,它将一个字符串转化为数字。

-- Lua
print(6.0 * 7.0 == '42')            --> false, 不同的类型
print(6.0 * 7.0 == tonumber('42'))  --> true, 都是 number 类型

Lua 的 <> 操作符在比较的值是不同的类型时将会得到 false。它们比较字符使用字符标排序,比较数字使用数字排序。

位操作符

Lua 5.3 引入了内置的位操作符,见下表。表中的操作符在 Lua 和 Javascript 中都可用。

操作符 含义
&
Ι
~ 取反
<< 左移

Lua 中的~,就像 Javascript 中的 ^。

-- Lua
print(6 & 18) -->  2;    00110b AND 10010b = 00010b.
print(6 | 18) --> 22;    00110b  OR 10010b = 10110b.
print(6 ~ 18) --> 20;    00110b XOR 10010b = 10100b.

Javascript 中区分了 >> 和 >>> 操作符, >> 保持符号而 >>> 使用 0 填充。Lua 中的 >> 就像 Javascript 中的 >>> 的操作符,使用 0 来填充空位。

这篇文章包含了一下基础知识,运行 Lua并理解 Lua 中的数据类型和表达式。下一篇文章将会包含更多的内容,比如Lua 的流程控制关键字,函数和很重要的 table。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
  • 序言:七十年代末,一起剥皮案震惊了整个滨河市,随后出现的几起案子,更是在滨河造成了极大的恐慌,老刑警刘岩,带你破解...
    沈念sama阅读 204,921评论 6 478
  • 序言:滨河连续发生了三起死亡事件,死亡现场离奇诡异,居然都是意外死亡,警方通过查阅死者的电脑和手机,发现死者居然都...
    沈念sama阅读 87,635评论 2 381
  • 文/潘晓璐 我一进店门,熙熙楼的掌柜王于贵愁眉苦脸地迎上来,“玉大人,你说我怎么就摊上这事。” “怎么了?”我有些...
    开封第一讲书人阅读 151,393评论 0 338
  • 文/不坏的土叔 我叫张陵,是天一观的道长。 经常有香客问我,道长,这世上最难降的妖魔是什么? 我笑而不...
    开封第一讲书人阅读 54,836评论 1 277
  • 正文 为了忘掉前任,我火速办了婚礼,结果婚礼上,老公的妹妹穿的比我还像新娘。我一直安慰自己,他们只是感情好,可当我...
    茶点故事阅读 63,833评论 5 368
  • 文/花漫 我一把揭开白布。 她就那样静静地躺着,像睡着了一般。 火红的嫁衣衬着肌肤如雪。 梳的纹丝不乱的头发上,一...
    开封第一讲书人阅读 48,685评论 1 281
  • 那天,我揣着相机与录音,去河边找鬼。 笑死,一个胖子当着我的面吹牛,可吹牛的内容都是我干的。 我是一名探鬼主播,决...
    沈念sama阅读 38,043评论 3 399
  • 文/苍兰香墨 我猛地睁开眼,长吁一口气:“原来是场噩梦啊……” “哼!你这毒妇竟也来了?” 一声冷哼从身侧响起,我...
    开封第一讲书人阅读 36,694评论 0 258
  • 序言:老挝万荣一对情侣失踪,失踪者是张志新(化名)和其女友刘颖,没想到半个月后,有当地人在树林里发现了一具尸体,经...
    沈念sama阅读 42,671评论 1 300
  • 正文 独居荒郊野岭守林人离奇死亡,尸身上长有42处带血的脓包…… 初始之章·张勋 以下内容为张勋视角 年9月15日...
    茶点故事阅读 35,670评论 2 321
  • 正文 我和宋清朗相恋三年,在试婚纱的时候发现自己被绿了。 大学时的朋友给我发了我未婚夫和他白月光在一起吃饭的照片。...
    茶点故事阅读 37,779评论 1 332
  • 序言:一个原本活蹦乱跳的男人离奇死亡,死状恐怖,灵堂内的尸体忽然破棺而出,到底是诈尸还是另有隐情,我是刑警宁泽,带...
    沈念sama阅读 33,424评论 4 321
  • 正文 年R本政府宣布,位于F岛的核电站,受9级特大地震影响,放射性物质发生泄漏。R本人自食恶果不足惜,却给世界环境...
    茶点故事阅读 39,027评论 3 307
  • 文/蒙蒙 一、第九天 我趴在偏房一处隐蔽的房顶上张望。 院中可真热闹,春花似锦、人声如沸。这庄子的主人今日做“春日...
    开封第一讲书人阅读 29,984评论 0 19
  • 文/苍兰香墨 我抬头看了看天上的太阳。三九已至,却和暖如春,着一层夹袄步出监牢的瞬间,已是汗流浃背。 一阵脚步声响...
    开封第一讲书人阅读 31,214评论 1 260
  • 我被黑心中介骗来泰国打工, 没想到刚下飞机就差点儿被人妖公主榨干…… 1. 我叫王不留,地道东北人。 一个月前我还...
    沈念sama阅读 45,108评论 2 351
  • 正文 我出身青楼,却偏偏与公主长得像,于是被迫代替她去往敌国和亲。 传闻我的和亲对象是个残疾皇子,可洞房花烛夜当晚...
    茶点故事阅读 42,517评论 2 343

推荐阅读更多精彩内容