类型与值

Lua是一种动态语言,没有定义类型的语法,每个值都携带了自身的类型信息。

Lua中有8种基础类型:nil、boolean、number、string、userdata、function、thread、table。函数type可以返回值的类型。

1
2
3
4
5
6
print(type("hello"))           --> string
print(type(1)) --> number
print(type(print)) --> function
print(type(true)) --> boolean
print(type(nil)) --> nil
print(type(type(X)) --> string

注:最后一行永远返回string。因为type函数总是返回一个字符串。

nil

nil是一种类型,它只有一个值nil。

boolean

boolean类型有两个可选值:false和true。在Lua中任何值都可以表示一个条件,只有当false和nil为假,其他情况都为真。

number

Lua的数字类型是双精度的浮点数。

string

Lua中的字符串是不可变的值。Lua中字符串和其他Lua对象一样,都是自动内存管理机制所管理的对象。字符串可以使用单引号或者双引号来界定。另外还可以使用[[]]来定义字符串,当中的字符不会被转义。

1
2
3
4
5
6
7
str = [[
<html>
<body>
hello "world"
</body>
</html>
]]

如果字符串中需要包含[[asd]]这样的字符,上面的定义就不好用了,所以可以在开始的[[之间加入任意数量的等号,就像[===[。这样修改之后只有遇到]===]算字符串结束。

字符串的连接操作符是

1
2
3
4
5
6
7
8
9
10

#### table

在Lua中,table是对象。可以看成是一种动态分配的对象。table的创建是通过“构造表达式”完成的,最简单的构造表达式就是{}。

table永远是匿名的。虽然任何值都可以作为table的索引,也可以用任何数字作为数组索引的起始值。但在Lua的习惯是,数组通常以1作为索引的起始值。

```lua
a = {}
a.a = "aaa"

对于未初始化的元素的索引结果都是nil。Lua将nil作为了界定数组结尾的标志。当一个数组中间含有nil的时候,长度操作符会认为这些 nil元素就的结尾标志。可以使用table.maxn,它将返回table的最大正索引数。

1
2
3
4
5
a = {}
a[100] = 1

print(#a) --> 0
print(table.maxn(a)) --> 100

算术操作符

Lua支持的算术操作符有:二元的‘+’,‘-’,‘*’,‘/’,‘^’,‘%’,一元的’-‘。

关系操作符

Lua支持的关系操作符:>、<、>=、<=、==、~=。

操作符==用于相等比较,~=用于不等比较。如果比较的两个值的类型不相同则肯定不相等。nil只有跟nil比较相等。对于table、userdata、function比较的是两个值的引用。

逻辑运算符

逻辑运算符有and、not、or。所有的逻辑运算符将false和nil视为假,其他的都视为真。
and和or都是短路求值,只有需要的时候才会求第二个操作数的值。

操作符and,如果第一个操作数为假那么返回第一个值,否则返回第二个值。
操作符or,如果第一个操作符为真那么返回第一个值,否者返回第二个值。
操作符not,永远只返回true或false。

1
2
3
4
5
print(4 and 5)           --> 5
print(nil and 13) --> nil
print(false and 13) --> false
print(4 or 5) --> 4
print(false or 5) --> 5

有一种常见的写法:x = x or v,这种写法等价于

not x then x
1
2
3
4
5
6
7
8

#### 字符串连接

Lua中字符串连接使用```..```,Lua中的字符串是不可变的值,连接字符串操作只会创建新的字符串不会对原来字符串进行修改。

```lua
print('a' .. 'b') --> ab
print(0 .. 1) --> 01

table构造式

构造式是用于创建和初始化table的表达式,最简单的构造式是{}。构造式还可以用于初始化数组。

1
2
3
strs = {'a', 'b', 'c'}  #会将strs[1]初始化为a,以此类推

a = {x=10, y=20}