LUA 快速上手

语言 Lua

Posted by gomyck on September 12, 2024

Lua 作为嵌入式脚本语言的一种, 提供了非常方便快速的逻辑实现能力, 并且在很多应用软件中, 都受到了很好的运行支持

安装

lua 的发行版本包类型非常多, 在主流操作系统中, 使用包管理器都可以很好的安装(yum apt-get brew)

源码安装

1
2
3
4
5
$ curl -L -R -O https://www.lua.org/ftp/lua-5.4.7.tar.gz
$ tar zxf lua-5.4.7.tar.gz
$ cd lua-5.4.7
$ make all test
$ make install

环境变量

1
2
3
# LUA_PATH
# 文件路径以 ";" 号分隔,最后的 2 个 ";;" 表示新加的路径后面加上原来的默认路径。
export LUA_PATH="~/lua/?.lua;;"

使用

lua 命令即可进入 live debug 模式

1
$ lua

语法

1
2
3
4
5
-- 注释

--[[
    多行注释
]]--

nil 是空, nil 做比较的时候应该给 nil 加双引号, 否则不能对比 type(X)==”nil” true

字符串连接, 使用 .. 连接, 而非 +

Table 的使用

lua table 是 key-value 的集合, 如果使用数组形式声明 table 的话, 那么 key 就是 index, 从 1 开始, 如果是字典形式, 则是 kv 对

1
2
3
4
5
6
7
tab = {"a", "b", "c"}
for i, v in pairs(tab) do
  print(i, v)
end
-- 1       a
-- 2       b
-- 3       c
1
2
3
4
5
6
7
tab = {x1="a", x2="b", x3="c"}
for i, v in pairs(tab) do
  print(i, v)
end
-- x1      a
-- x3      c
-- x2      b

变量的声明

变量的定义, 基本按照大多数语言(如 java)规范来命名, 所以, 只要不是故意启用奇葩的名称, 基本不会有语法上的错误

1
2
3
4
5
a = 5               -- 全局变量
local b = 5         -- 局部变量
c = "hel" .. "lo"   -- 字符串拼接
d, e = 10, 2*x
f[i], f[j] = f[j], f[i] -- swap

循环

可以使用 breakcontinue 来退出循环

允许嵌套循环

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
-- 常见的 while 循环
while (true) do
  print("hello")
end

-- i 初始为 10, 每执行循环一次减 1, 减到 1 时最后一次进入循环体, 然后停止
for i=10,1,-1 do
  print(i) -- 10 ...... 1
end

-- 执行一次 f(), 后续循环不在执行
function f(x)
  print("function")
  return x*2
end
for i=1,f(5) do
  print(i)
end

流程控制

1
2
3
4
5
6
--[ 0 为 true ]
if(0) then
  print("0 为 true")
else
  print("1 为 false")
end

函数

1
2
3
4
5
6
7
8
9
function f(...)
  a = select(3, ...)     -->从第三个位置开始,变量 a 对应右边变量列表的第一个参数
  print (a)
  print (select(3,...)) -->打印所有列表参数
end
f(0,1,2,3,4,5)

-- 2
-- 2       3       4       5

运算符

与 python 类似

模块

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
-- 文件名为 module.lua
-- 定义一个名为 module 的模块
module = {}
-- 定义一个常量
module.constant = "这是一个常量"
-- 定义一个函数
function module.func1()
    io.write("这是一个公有函数!\n")
end
local function func2()
    print("这是一个私有函数!")
end
function module.func3()
    func2()
end
return module
1
2
3
4
5
-- test_module.lua 文件
-- module 模块为上文提到到 module.lua
require("module")
print(module.constant)
module.func3()

C调用

1
2
3
-- 或者 path = "C:\\windows\\luasocket.dll"
local path = "/usr/local/lua/lib/libluasocket.so"
local f = loadlib(path, "luaopen_socket")

IO

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
-- 以只读方式打开文件
file = io.open("test.lua", "r")
-- 设置默认输入文件为 test.lua
io.input(file)
-- 输出文件第一行
print(io.read())
-- 关闭打开的文件
io.close(file)
-- 以附加的方式打开只写文件
file = io.open("test.lua", "a")
-- 设置默认输出文件为 test.lua
io.output(file)
-- 在文件最后一行添加 Lua 注释
io.write("--  test.lua 文件末尾注释")
-- 关闭打开的文件
io.close(file)

内置函数

  1. 数学函数
    • math.abs(x):返回 x 的绝对值。
    • math.acos(x):返回 x 的反余弦值。
    • math.asin(x):返回 x 的反正弦值。
    • math.atan(x):返回 x 的反正切值。
    • math.ceil(x):返回大于或等于 x 的最小整数。
    • math.cos(x):返回 x 的余弦值。
    • math.deg(x):将弧度转换为角度。
    • math.exp(x):返回 e 的 x 次幂。
    • math.floor(x):返回小于或等于 x 的最大整数。
    • math.log(x):返回 x 的自然对数。
    • math.max(x, ...):返回参数中的最大值。
    • math.min(x, ...):返回参数中的最小值。
    • math.rad(x):将角度转换为弧度。
    • math.random([m [, n]]):返回一个随机数。
    • math.sin(x):返回 x 的正弦值。
    • math.sqrt(x):返回 x 的平方根。
    • math.tan(x):返回 x 的正切值。
  2. 字符串函数
    • string.byte(s [, i [, j]]):返回字符串 s 中第 i 个到第 j 个位置字符的 ASCII 值。
    • string.char(...):将参数转换为字符并连接成字符串。
    • string.find(s, pattern [, init [, plain]]):在字符串 s 中查找模式 pattern。
    • string.format(formatstring, ...):返回格式化后的字符串。
    • string.gmatch(s, pattern):返回一个迭代函数,能遍历字符串 s 中所有匹配 pattern 的子串。
    • string.gsub(s, pattern, repl [, n]):替换字符串 s 中的 pattern 为 repl。
    • string.len(s):返回字符串 s 的长度。
    • string.lower(s):将字符串 s 转换为小写。
    • string.match(s, pattern [, init]):在字符串 s 中匹配 pattern。
    • string.rep(s, n):返回字符串 s 重复 n 次的结果。
    • string.reverse(s):返回字符串 s 的反转。
    • string.sub(s, i [, j]):返回字符串 s 的子串,从 i 到 j(默认到字符串末尾)。
    • string.upper(s):将字符串 s 转换为大写。
  3. 表函数
    • table.concat(table [, sep [, i [, j]]]):将表中元素连接成字符串。
    • table.insert(table, [pos,] value):在表的指定位置插入值。
    • table.maxn(table):返回表中最大的正整数索引。
    • table.remove(table [, pos]):移除表中指定位置的元素。
    • table.sort(table [, comp]):对表进行排序。
  4. I/O 函数
    • io.close([file]):关闭文件。
    • io.flush():刷新当前的输出文件。
    • io.input([file]):设置输入文件。
    • io.lines([filename]):返回一个迭代函数,遍历文件每一行。
    • io.open(filename [, mode]):以指定模式打开文件。
    • io.output([file]):设置输出文件。
    • io.read(...):从文件中读取内容。
    • io.write(...):向文件中写入内容。
  5. 其他常用函数
    • assert(v [, message]):如果 v 为假则触发错误。
    • collectgarbage(opt [, arg]):控制垃圾收集器。
    • dofile(filename):运行指定文件中的 Lua 代码。
    • error(message [, level]):中止执行并返回错误信息。
    • getmetatable(object):返回对象的元表。
    • ipairs(t):返回一个迭代函数,用于遍历数组部分。
    • next(table [, index]):返回下一个键值对。
    • pairs(t):返回一个迭代函数,用于遍历表。
    • pcall(f, arg1, ...):以保护模式调用函数。
    • print(...):输出到标准输出。
    • rawequal(v1, v2):判断两个值是否相等。
    • rawget(table, index):直接获取表中指定索引的值。
    • rawset(table, index, value):直接设置表中指定索引的值。
    • require(modname):加载模块。
    • setmetatable(table, metatable):设置表的元表。
    • tonumber(e [, base]):将字符串转换为数字。
    • tostring(e):将值转换为字符串。
    • type(v):返回值的类型。
    • xpcall(f, err):以保护模式调用函数,并指定错误处理函数。