碳基体

奋斗在产品安全第一线的安全妹子

lua cheatsheet(烂俗名:如何快速学lua)

lua由于其高性能的特征,被广泛应用于game与server编程。对web领域的人,ngx_lua是必备技能,如何快速的入门呢?(要学的好还是得learn xxx the hard way),就是快速浏览了基本语法后,站在前人的总结下前进。


一、lua基本语法

(1)lua有哪些数据类型? nil,boolean,number,string,table,function,userdata,thread

(2)lua有哪些操作符?算术操作符,关系操作符,逻辑操作符,字符串连接,操作符优先级,table构造式

(3)lua的语句块,控制结构?赋值操作;do-end语句块;if-then-else-end;while-do-end;repeat-untl;for-do=end;break,return

(4)lua函数编写方式?什么是第一类值?什么是词法域?什么是闭包?什么是尾调?

(5)lua错误处理与调试?assert,pcall,debug

(6)什么是metatable,metamethod?

(7)如何使用第三方模块?如何编写自己的模块?require,module

(8)lua有哪些标准库?(标准库与第三方库的丰富程度决定了绝对新手的开挂程度)math,bitwise,table,string,I/O, OS,debug库(字符串操作,输入输出操作是变成中最最基本的实际需求)

(9)如何与C代码进行交互?lua作为解释型语言,特性就是其能够非常轻易的生成动态执行代码?lua作为性能大能语言,特性就是c模块的无缝连接-动态连接机制? package.loadlib



二、lua语言特别的地方

(1)table是lua中主要的仅有的数据结构机制,table是一个动态分配的对象,程序仅持有一个对他们的引用(或指针),lua 不会暗中产生table的副本或创建新的table。table的创建是通过构造表达式完成的. 

(2)lua数组通常以1作为索引的起始值

(3)长度操作符(#)以nil元素为结尾标记

(4) lua将值false和nil视为价,其余为真

(5)函数是第一类值,函数可以存储在变量中,可以通过参数传递给其他函数,还可以作为其他函数的返回值

 (6) 使用 ~= 用作不等性操作(其他语言一般用 !=)

(7) 对于table,userdata,function,lua是作引用比较的,只有当它们引用同一个对象时,才认为它们相等

(8)词法域与闭包的概念:当一个函数内部嵌套另一个函数定义时,内部的函数体可以访问外部的函数的局部变量

(9)dofile与loadfile与loadstring的区别:dofile 每次都编译;loadfile  编译代码成中间码并且返回编译后的chunk作为一个函数,而不执行代码。loadfile只需要编译一次,但可以多次运行;loadstring 与loadfile相似,只不过它不是从文件里读入chunk,而是从一个串中读入

(10)使用table构造式描述数据文件使得lua在数据文件处理上事半功倍,2M数据不到1s

(11)metatable与metamethod的概念,通常,lua中的每个值都有一套预定义的操作集合。可以通过元表来修改一个值得行为,使其在面对一个非预定义的操作时执行一个指定的操作。lua中的每个值都有一个元表,table和userdata可以有各自独立的元表,而其他类型的值则共享其类型所属的单一元表。lua在创建新的table时不会创建元表,可以使用setmetatable来设置或修改任何table的元表。在lua代码中,只能设置table的元表,若要设置其他类型的值的元表,则必须通过C代码来完成。lua会检测一个操作中的值是否有元表,这些元表中是否定义了关于此操作的元方法。

(12)在lua中,()空白捕获它在目标字符串中的位置

(13)lua没有整数类型,lua中的数字可以表示任何32位整数,而不会产生四舍五入的错误

(14)lua的字符串是不可变的值,lua程序中操作100k或1M的字符串是很常见的,可以通过数值\ddd来指定字符串中的字符 

(15)lua字符串界定符,可以用一对匹配的双方括号(两个方括号加上任意数量的等号)来界定一个字母字符串,lua不会解释其中的转义序列。此外,如果字符串的第一个字符是一个换行符号,lua会忽略它。这种写法对书写含有程序代码的字符串尤为有用

(16)泛型for的理解(更深入点,对迭代器的理解),ipairs与pairs的区别,pairs 迭代table元素,ipairs 迭代数组元素, ipairs从下标为1开始遍历,然后下标累加1,如果某个下标元素不存在就终止遍历。这就导致如果下标不连续或者不是从1开始的表就会中断或者遍历不到元素


p.s.最最喜欢的就是everything is table与函数第一类值特性


三、性能优化点 

(1)尽可能使用局部变量(其实是个时空平衡问题,local变量访问速度要快但是增加了本地变量的创建和消耗)

(2)当需要创建非常多的小size表的时候,最好预先填写表的大小

(3)在大字符串连接时,我们应避免..,应用table来模拟buffer,然后concat得到最终字符串

(4)把循环中不变的东西放到循环外来创建

(5) x.y 比x:y 快



四、良好的编程习惯

(1)使用pcall来进行错误与异常的处理是非常好的习惯(来自血的教训)

(2)使用变量前先判断是否为nil(来自血的教训)

(3)在做lua编程的时候,一般会把性能瓶颈的部分交给c来实现(游戏行业更显著),但是,如果使用luajit(在不修改代码的情况下可以获得平均5倍的加速),要注意c的代码越多,luajit优化的幅度越小,尝试尽可能的用lua来实现功能,会带来意想不到的效果哦

(4)遵循lua编程规范 



五、应用

1. server

下一篇文章说说nginx与luajit的快速结合


2. game

虽然离开了游戏行业,但一直关注着大牛们的动态,最喜欢的有云风 


后续:

1. 使用lua table做配置文件超级赞

local M = {


}

return M

。。。


参考:

《lua程序设计》第三版

http://wuzhiwei.net/lua_performance/

http://lua-users.org/wiki/LuaStyleGuide

来源:碳基体

评论