Upgrade to Pro — share decks privately, control downloads, hide ads and more …

Introduction to Lua

Introduction to Lua

Most popular scripting languages now contain many paradigm specific and platform specific features that increase the complexity of the language. Few of these languages are simple enough to be embedded in existing applications easily. Lua's extensibility and simplicity makes it an ideal choice for embedded scripting. Lua is often embedded in video games, desktop GUI applications, server software, and even mobile applications. This talk covers the basics of the Lua. I will demonstrate how Lua's simplicity allows for quick development of small utility scripts. I will also show how Lua's powerful meta-mechanisms allow for rapid development of software in prototypal OO, classical OO, and functional paradigms. At the end of the talk I will integrate Lua into an existing application.

Trevor Brown

August 26, 2015
Tweet

More Decks by Trevor Brown

Other Decks in Programming

Transcript

  1. Lua

  2. Lua • Interpreted scripting language • Dynamically typed • Automatic

    memory management • Multi-paradigm – procedural, classical OO, prototypal OO, and functional • Created in 1993 by Roberto Ierusalimschy • Open source – release under the MIT license • Extremely small (source code and documentation archive is under 1 MB) Lua
  3. Lua's Strengths • Simple – Lua has relatively few programming

    constructs • Efficient – Lua is one of the fasted interpreted languages today. LuaJIT makes it even faster http://luajit.org/ • Portable – Lua is written in ANSI C • Extensible – Lua can be easily extended with C code – Can also easily interface with many other languages Lua
  4. Where should Lua be used? • Education – Lua's simplicity

    makes it a good first language – Similar to JavaScript • Places low latency scripting is required – Lua's efficiency and simplicity make an ideal choice • Places application portability is required – Any architecture that can execute C code can run Lua • Embedded Scripting – Easy to embed in existing enterprise applications
  5. Where is Lua Used? • Redis • Wireshark • Freeswitch

    • Both Nginx and Apache have Lua modules • NeoVim • MineCraft (and many other games)
  6. Who Uses Lua? • GitHub – GitHub Pages routing http://githubengineering.com/rearchitecting-github-pages/

    • Cloudflare – Firewall and HTTP request preprocessor http://openresty.org/ • Adobe – Photoshop Lightroom https://www.adobe.com/devnet/photoshoplightroom.html • Lego Mindstorms NXT – scripting http://shop.lego.com/en-US/Mindstorms-EV3
  7. Comments and Strings ­­ comments start with two dashes ­­[[

    adding two square brackets makes the comments multi­line ­­]] string = 'single quoted strings' another_sting = "are the same as double quoted" multiline = [[ foo bar ]] ­­ strings can be concatenated with `..` both = 'one' .. ' two three' print(both) ­­> 'one two three'
  8. Numbers ­­ all numbers are double precision floating ­­ point

    values (IEEE 754 floats) Num = 42 ­­ arithmetic expressions that can return integer values will num3 = num / 7 ­­> 6.0 equal = (6 == num3) ­­> true ­­ (6 == 6.0) ­­ some can't and will return floats num2 = num / 9 ­­> 4.6666666666667 num4 = num + 0.5 ­­> 42.5 ­­ http://lua­users.org/wiki/NumbersTutorial
  9. Booleans booleanValue = true ­­ `not` can be used to

    invert boolean values oppositeValue = not booleanValue ­­> false definitelyBoolean = not not booleanValue ­­> true if not oppositeValue then print('it was false') end ­­> it was false ­­ `not` coerces other types to booleans ­­ all values except nil and false are truthy print(not 'a') ­­> false print(not not 'a') ­­> true
  10. Tables empty = {} ­­ tables are key value stores

    user = {name = 'Roberto', favorite_language = 'Lua'} ­­ similar to JavaScript objects, only no methods exist on the table user2 = {name = 'Joe', favorite_language = 'Erlang'} ­­ but you can add your own functions to the table user2.print_func = print ­­ looking up the value of a string key is trivial firstname = user2.name ­­> 'Joe' firstname = user2['name'] ­­> 'Joe'
  11. Tables (cont.) ­­ both keys and values can of any

    type, but by default keys are strings numbers = {[12] = 'twelve', [13] = 'thirteen', [14] = 'fourteen'} ­­ tables can represent arrays array = {'a', 'b', 'c'} ­­ this is really a table. it is stored as this: ­­ {1 = 'a', 2 = 'b', 3 = 'c'} ­­ getting the length of array is easy length = #array ­­> 3
  12. Tables (cont.) ­­ iterating over tables is trivial print_table =

    function (table) for k, v in pairs(table) do print('key:', k, 'value:', v) end End print_table(user) ­­> key: name value: Roberto ­­> key: favorite_language value: Lua print_table(array) ­­> key: 1 value: a ­­> key: 2 value: b ­­> key: 3 value: c
  13. Nil ­­ when a key is missing in a table

    nil is returned table = {} print(table.nonExistent) ­­> nil ­­ setting a variable to nil allows the value of the variable to be garbage collected largeValue = nil ­­ `largeValue` will now be removed from memory
  14. Functions function add (a, b) return a + b end

    add(2,3) ­­> 5 ­­ closures and anonymous functions are possible function multiply_by(x) return function (y) return y * x end end double = multiply_by(2) ­­ functions are first class double(8) ­­> 16
  15. Functions (cont.) ­­ recursive functions are possible function factorial(num, acc)

    acc = acc or 1 if num == 0 then return acc else return factorial(num ­ 1, num * acc) end end ­­ all parameters need not be present factorial(6) ­­ in this case `acc` will default to nil ­­> 720
  16. Functions (cont.) ­­ functions calls can return multiple values function

    multiples_of(num) return 1 * num, 2 * num, 3 * num end multiples_of(4) ­­ > 4 8 12 ­­ functions can take a variable number of arguments function add_all(...) local sum = 0 for index, value in ipairs{...} do sum = sum + value end return sum end add_all(1,2,3,4) ­­> 10
  17. Scope global_scope = _G ­­ variables in the global scope

    are really attributes on `_G` print(global_scope == _G.global_scope) ­­> true ­­ variables can be local to the block they are declared in if x > 1 then local y = 10 print(y) end print_lang = function () local lang = 'Lua' print(lang) end
  18. Metatables ­­ metatables can contain various attributes that are read

    by Lua when performing certainly operations. defaults = {favorite_language = 'Lua'} defaults.__index = defaults user = {} ­­ if we set `defaults` as the metatable lua will check the table assigned to the metatables `__index` attribute if a key is missing setmetatable(user, defaults) print(getmetatable(user)) ­­> table: 0x15ebe60 print(user.favorite_language) ­­> 'Lua'
  19. Metatables defaults defaults = { favorite_language = 'Lua' } defaults.__index

    = defaults user = {} setmetatable(user, defaults) print(user.favorite_language) ­­> 'Lua' ­­ what happens on that last line? print(user.favoritie_language) user Lookup favorite_language Key missing check metatable defaults' __index is itself Lookup favorite_language on defaults and return the value
  20. Objects local User = {} User.__index = User function User:new(first_name,

    last_name, favorite_language) local user = { first_name = first_name, last_name = last_name, favorite_language = favorite_language } setmetatable(user, User) return user end
  21. Objects ­­ this: function User:display_name() return self.first_name .. ' '

    .. self.last_name end ­­ is the same as this: function User.display_name(self) return self.first_name .. ' ' .. self.last_name end User.__tostring = User.display_name local u = User:new('Joe', 'Armstrong', 'Erlang') print(u:display_name()) ­­> 'Joe Armstrong' print(u) ­­> 'Joe Armstrong'
  22. Conclusion • Lua is great for small standalone applications •

    Great for embedded applications or for embedding inside existing applications • Great language for scripting in general • Great for education • Definitely some quirks that take getting used to
  23. Quirks • No variable incrementing shortcut (e.g a += 1)

    • Not equal is `~=` (e.g. a ~= 2) • But `~(a == 2)` is invalid. It must be `not (a == b)` • Ternary operator ugly – Local square = is_square(box) and “it's a square” or “not a square” • Table indices start at 1