🌙 Lua — 1993

⬅️ Atlas · 🗂️ Todas las fichas · 📚 Índice de clases

Lua nació en Brasil para que unos ingenieros de Petrobras pudieran configurar simulaciones sin recompilarlas, y hoy es el lenguaje incrustado más usado del mundo: está en World of Warcraft, en Roblox, en Redis, en Nginx y en las plantillas de Wikipedia. Su intérprete completo cabe en unos 200 kilobytes.

🎯 Por qué está en este programa

Lua es un primo de la familia de scripting dinámico (Atlas) y uno de los tres primos verificados en CI, junto a Ruby y Perl.

Aporta al programa el caso central de una clase entera: incrustar un lenguaje en otro (clase 163), con las cuatro decisiones que eso obliga a tomar. Y aporta la tabla como estructura única (clase 099) y las corrutinas (clase 134) en su forma más simple.

Año 1993; 5.1 (2006) es la base de LuaJIT; 5.4 la actual
Autoría Roberto Ierusalimschy, Luiz Henrique de Figueiredo, Waldemar Celes — PUC-Rio, Brasil
Familia Scripting dinámico; con influencia de Scheme y de lenguajes de configuración
Paradigma Multiparadigma; OO por prototipos, con metatablas
Tipado Dinámico, con ocho tipos en total
Memoria Recolector incremental o generacional
Ejecución Bytecode sobre una VM de registros; LuaJIT compila a nativo
Estado 🟢 Dominante como lenguaje incrustado; licencia MIT

📜 Historia

En 1993, el grupo Tecgraf de la Pontificia Universidad Católica de Río de Janeiro trabajaba para Petrobras. Los ingenieros necesitaban configurar programas de simulación y visualización de datos geológicos, y los ficheros de configuración se les habían quedado cortos: querían condicionales, cálculos y variables (clase 163).

Y había una restricción de contexto que resultó decisiva: Brasil tenía una política de reserva de mercado para la informática, así que comprar software extranjero era difícil. Tuvieron que hacerlo ellos.

Diseñaron Lua —"luna" en portugués— con unos objetivos muy concretos que explican todo lo demás:

  1. Que se pueda incrustar en un programa de C con una API pequeña.
  2. Que sea diminuto y portable: C89 puro, sin dependencias.
  3. Que sea rápido.
  4. Y que un ingeniero que no es programador pueda escribirlo.

LuaJIT (Mike Pall, 2005) llevó el rendimiento a otro nivel: es uno de los compiladores JIT más rápidos que existen para un lenguaje dinámico, y sigue basado en Lua 5.1 — lo que ha partido el ecosistema en dos ramas que conviven.

Y el momento en que el mundo lo conoció fue World of Warcraft (2004), que expuso toda su interfaz como guiones Lua y creó un ecosistema de miles de complementos escritos por jugadores.

🏭 Dónde vive hoy

🧠 Lo que enseña: hacer mucho con muy poco

Uno, la tabla es la única estructura de datos (clase 099):

local t = {}
t[1] = "primero"          -- array
t.nombre = "Ana"           -- registro
t["clave"] = valor          -- diccionario

Arreglo, registro, diccionario, objeto, espacio de nombres y módulo son la misma cosa. Es minimalismo llevado al extremo, y funciona: la biblioteca estándar entera se construye con tablas.

Dos, las metatablas dan orientación a objetos sin tenerla:

local Cuenta = {}
Cuenta.__index = Cuenta        -- ← si no encuentras el campo, búscalo aquí

function Cuenta.new(saldo)
  return setmetatable({saldo = saldo}, Cuenta)
end
function Cuenta:depositar(x) self.saldo = self.saldo + x end

__index es la herencia por prototipos (clase 112), la misma idea que JavaScript y Self — construida con el mecanismo general de metatablas, que también permite sobrecargar operadores y controlar el acceso.

Y tres, las corrutinas (clase 134), que Lua tiene desde 1993:

local co = coroutine.create(function()
  for i = 1, 3 do coroutine.yield(i) end
end)
print(coroutine.resume(co))   -- true 1

Multitarea cooperativa con una pila propia, que es la base de los generadores y de async/await de casi todos los lenguajes modernos.

Y para la clase 163, lo importante es cómo se incrusta:

lua_State *L = luaL_newstate();
luaL_openlibs(L);                     /* ← o NO abrirlas: se elige QUÉ existe */
lua_register(L, "dibujar", c_dibujar);
luaL_dofile(L, "config.lua");
lua_close(L);

La línea comentada es la clave y es la razón de su éxito: un estado de Lua recién creado no tiene io, ni os, ni nada. El anfitrión abre las bibliotecas que quiera y registra las funciones que quiera. Es el modelo de capacidades de la clase 153, integrado en el diseño — y por eso Wikipedia puede ejecutar plantillas escritas por cualquiera sin que tumben el servidor.

🔄 Lo que se ha modernizado

⚙️ Cómo se ejecuta hoy

lua main.lua < entrada.txt        # el comando de la clase 041
luajit main.lua                    # el JIT, muy superior en cálculo

luarocks install <paquete>

🧪 El programa de la clase 041 en Lua

Esta versión se ejecuta y se verifica en CI.

local precio, cantidad, descuento = io.read("n", "n", "n")
local total = precio * cantidad * (1 - descuento)
print(string.format("Total: %.2f", total))

Lo que hay que ver.

📚 Fuentes y bibliografía


⏮️ Volver al Atlas · 🗂️ Todas las fichas · 🔗 Relacionadas: Tcl · JavaScript · Python · C