Lua边学边记

Lua语法

变量

简单4中变量类型

  • number

    表示双精度类型的实浮点数

  • string

    字符串由一对双引号或单引号来表示

  • boolean

    包含两个值:falsetrue

  • nil

复杂4种变量类型

  • function 函数

    CLua 编写的函数

    • 闭包实现

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      15
      16
      17
      local x = 20

      function Foo(x)
      return function(y)
      print(string.format("2=======> x: %d", x))
      return x + y
      end
      end

      function Bar()
      print("Bar")
      end

      foo = Foo(x)
      x = 30
      print(string.format("1=======> x: %d", x))
      print(foo(10))
      1
      2
      3
      4
      5
      输出:
      1=======> x: 30
      2=======> x: 20
      30
      [Finished in 58ms]
  • table

    Lua 中的表(table)其实是一个”关联数组”(associative arrays),数组的索引可以是数字、字符串或表类型。在 Lua 里,table 的创建是通过”构造表达式”来完成,最简单构造表达式是{},用来创建一个空表。

  • userdata 数据结构

    表示任意存储在变量中的C数据结构

  • thread 协同程序

    表示执行的独立线路,用于执行协同程序

面向对象

面向对象特征

  • 封装:能够把一个实体的信息、功能、响应等都装入一个单独的对象中
  • 继承:继承的方法允许在不改动原程序的基础上对其进行扩充,这样使得原功能得以保存,而新功能也得以扩展。这有利于减少重复代码,提高软件开发效率
  • 多态:同一操作作用于不同的对象,可以有不同的解释,产生不同的执行结果。在运行时,可以通过指向基类的指针来调用实现派生类中的方法。
  • 抽象:抽象(Abstraction)是简化复杂的实现问题的途径,它可以为具体问题找到最恰当的类定义,并且可以在最恰当的继承级别解释问题

示例

  • LUA中的类可以通过 table + function 模拟,继承可以通过 metetable 模拟

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    Rectangle = {area = 0, length = 0, breadth = 0}
    -- 派生类的方法 new
    function Rectangle:new (o, length, breadth)
    o = o or {}
    setmetatable(o, self)
    self.__index = self;
    self.length = length or 0
    self.breadth = breadth or 0
    self.area = length * breadth;
    return o;
    end

    function Rectangle:printArea()
    print(string.format("矩形面积为:%d", self.area))
    end

    r = Rectangle:new(nil, 10, 20)
    r:printArea()
  • 继承

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    Shape = { area = 0 }
    function Shape:new(o, side)
    o = o or {}
    setmetatable(o, self)
    self.__index = self
    side = side or 0
    self.area = side * side
    return o
    end

    function Shape:printArea()
    print(string.format("面积为:%d", self.area))
    end

    myShape = Shape:new(nil, 10)
    myShape:printArea()

    Square = Shape:new()
    function Square:new(o, side)
    o = o or Shape:new(o, side)
    setmetatable(o, self)
    self.__index = self
    return o
    end

    -- 重写函数
    function Square:printArea()
    print(string.format("正方形面积为:%d", self.area))
    end

    mySquare = Square:new(nil, 15)
    mySquare:printArea()

    Rectangle = Shape:new()
    function Rectangle:new(o, length, breadth)
    o = o or Shape:new(o)
    setmetatable(o, self)
    self.__index = self
    self.area = length * breadth
    return o
    end

    -- 重写函数
    function Rectangle:printArea()
    print(string.format("矩形面积为:%d", self.area))
    end

    myRectangle = Rectangle:new(nil, 10, 20)
    myRectangle:printArea()
  • .: 的区别在于使用 : 定义的函数隐含 self 参数,使用 : 调用函数会自动传入 tableself 参数

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    local person = {
    name = "Alice",
    greet = function(self)
    print("Hello, " .. self.name)
    end
    }

    person:greet() -- 输出 "Hello, Alice"
    person.greet(person) -- 输出 "Hello, Alice"

top