Linguagem Lua

LUA

Grupo responsável:

  • Alex Bertei
  • Gerson Porciúncula Siqueira
  • Italo Menna Silveira

História

Lua é inteiramente projetada, implementada e desenvolvida no Brasil, por uma equipe na PUC-Rio (Pontifícia Universidade Católica do Rio de Janeiro). Lua nasceu e cresceu no Tecgraf, o Grupo de Tecnologia em Computação Gráfica da PUC-Rio. Atualmente, Lua é desenvolvida no laboratório Lablua. Tanto o Tecgraf quanto Lablua são laboratórios do Departamento de Informática da PUC-Rio. A primeira versão de Lua (1.0) é de julho de 1993. A primeira versão pública (1.1) é de julho de 1994. A versão mais recente da Lua é a 5.2.
A motivação para a criação de Lua no Tecgraf foi a necessidade crescente das suas aplicações serem configuráveis externamente pelos usuários. Isso quer dizer que diversos aspectos essenciais das aplicações podem ser modificados sem recompilar a aplicação. Desde o início, nas aplicações criadas no Tecgraf, esse tipo de configuração era muito mais do que simplesmente poder escolher a cor da janela ou o tipo de fonte de texto: era necessário poder tomar decisões em tempo de execução que somente os usuários sabiam quais eram. Sendo assim, era necessário fornecer algum tipo de programação para os usuários finais. Um outro tipo de configuração era a descrição de complexos relatórios e análises feitas pela Petrobras por encomenda ao Tecgraf. Mais uma vez, essa descrição não podia estar congelada dentro da aplicação pois cada usuário tinha uma necessidade diferente e que mudava a cada tarefa. O Tecgraf tinha portanto (e ainda tem) forte demanda para aplicações que fossem configuráveis externamente, tanto descrevendo que decisões deveriam ser tomadas quanto descrevendo quais dados seriam usados e como eles seriam usados.
Após projetar e usar com sucesso duas pequenas linguagens específicas para cada uma dessas tarefas, o Tecgraf decidiu investir na criação de uma linguagem única que pudesse atender a todas as necessidades de configuração das suas aplicações. Assim nasceu Lua: uma linguagem procedural simples com poderosas construções para descrição de dados. Desde então Lua tem sido usada em inúmeros projetos no Tecgraf e vem ganhando também uma enorme popularização pelo mundo e usada em distintos tipos de aplicações.

A linguagem

É uma linguagem de programação poderosa, rápida e leve, projetada para estender aplicações, combina sintaxe simples para programação procedural com poderosas construções para descrição de dados baseadas em tabelas associativas e semântica extensível. Lua é tipada dinamicamente, é interpretada a partir de bytecodes para uma máquina virtual baseada em registradores, e tem gerenciamento automático de memória com coleta de lixo incremental. Essas características fazem de Lua uma linguagem ideal para configuração, automação (scripting) e prototipagem rápida.

Características

  • Estabelecida e robusta: Lua é usada em muitas aplicações industriais, com ênfase em sistemas embutidos e jogos . Lua é atualmente a linguagem de script mais usada em jogos. Lua tem um sólido manual de referência e existem vários livros sobre a linguagem. Várias versões de Lua foram lançadas e usadas em aplicações reais desde a sua criação em 1993.
  • Rápida: Lua tem uma merecida reputação de ótimo desempenho. Outras linguagens de script aspiram ser “tão rápidas quanto Lua”. Vários benchmarks mostram Lua como a linguagem mais rápida dentre as linguagens de script interpretadas. Lua é rápida não só em programas específicos para benchmarks, mas no dia-a-dia também. Porções substanciais de aplicações grandes são escritas em Lua.
  • Embutível: Lua é uma engine rápida e pequena que você pode facilmente embutir na sua aplicação. Lua tem uma API simples e bem documentada que permite uma integração forte com código escrito em outras linguagens. É simples estender Lua com bibliotecas escritas em outras linguagens. Também é simples estender programas escritos em outras linguagens com Lua. Lua é usada para estender programas escritos não só em C e C++, mas também em Java, C#, Smalltalk, Fortran, Ada, Erlang, e mesmo outras linguagens de script, como Perl and Ruby.
  • Poderosa (simples): Um conceito fundamental no projeto de Lua é fornecer meta-mecanismos para a implementação de construções, em vez de fornecer uma multidão de construções diretamente na linguagem. Por exemplo, embora Lua não seja uma linguagem puramente orientada a objetos, ela fornece meta-mecanismos para a implementação de classes e herança. Os meta-mecanismos de Lua trazem uma economia de conceitos e mantêm a linguagem pequena, ao mesmo tempo que permitem que a semântica seja estendida de maneiras não convencionais.
  • Pequena: Incluir Lua numa aplicação não aumenta quase nada o seu tamanho. O pacote de Lua 5.2.0, contendo o código fonte e a documentação, ocupa 241K comprimido e 950K descompactado. O fonte contém cerca de 20000 linhas de C. No Linux, o interpretador Lua contendo todas as bibliotecas padrões de Lua ocupa 182K e a biblioteca Lua ocupa 240K.
  • Livre: Lua é software livre de código aberto, distribuída sob uma licença muito liberal (a conhecida licença MIT). Lua pode ser usada para quaisquer propósitos, incluindo propósitos comerciais, sem qualquer custo ou burocracia.
  • Tem importância global: O projeto e a evolução de Lua foram apresentados em junho de 2007 na HOPL III, a 3a Conferência da ACM sobre a História das Linguagens de Programação. Essa conferência ocorre a cada 15 anos (a primeira foi em 1978 e a segunda em 1993) e somente poucas linguagens são apresentadas a cada vez. A escolha de Lua para a HOPL III é um importante reconhecimento do seu impacto mundial. Lua é a única linguagem de programação de impacto desenvolvida fora do primeiro mundo, estando atualmente entre as 20 linguagens mais populares na Internet (segundo o índice TIOBE).

Linguagem de extensão

Classifica-se as linguagens de extensão ou de script segundo a sua complexidade:

  • Linguagens de configuração: Servem para selecionar preferências e são tipicamente uma lista de valores associados a variáveis. Um exemplo típico são os arquivos .ini do Windows.
  • Linguagem de Macros: Servem para automação de tarefas e são tipicamente uma lista de ações primitivas, com muito pouco ou nenhum controle de fluxo. Um exemplo típico são os arquivos de automação de conexões internet via modem.
  • Linguagem de extensão: Permitem acesso programável aos serviços da aplicação, com fluxo de controle completo e funções definidas pelo usuário a partir de primitivas exportadas pela aplicação. Essas linguagens são linguagens completas, muitas vezes variantes simplificadas de linguagens tradicionais como Lisp ou C.


Independente da complexidade da linguagem, a adoção de uma linguagem de extensão é uma técnica poderosa de desenvolvimento de software, pois permite que muitos aspectos da aplicação sejam controlados externamente, a partir de arquivos textos facilmente editados pelo programador ou pelo usuário, sem necessidade de recompilar a aplicação. Isso torna o desenvolvimento mais ágil, pois permite que partes importantes da aplicação sejam desenvolvidas por outros membros da equipe que não são programadores profissionais (no caso de jogos, animadores e artistas).
Além disso, a adoção de uma mesma linguagem para várias tarefas na aplicação permite um aumento importante de produtividade global, pois não é necessário definir, documentar e manter vários formatos diferentes. Para o usuário da aplicação, isso se traduz no re-aproveitamento automático (e inconsciente) dos conceitos aprendidos para realizar as várias tarefas, encorajando a exploração.

Como usar?

A linguagem Lua conta com uma única implementação principal, mantida pelos autores da linguagem no site www.lua.org, mas essa implementação conta com diversas distribuições mantidas por desenvolvedores independentes.
Em muitos usos reais de Lua, o interpretador é distribuido embutido na aplicação final. Afinal, um dos principais objetivos de Lua é exatamente esse tipo de uso. Nesses casos, detalhes de como usar Lua são dependentes da aplicação. Esses detalhes incluem que editor usar, onde e como armazenar os programas, como executar um programa, etc. Neste texto, como não estamos visando nenhuma aplicação particular, vamos usar o interpretador independente (stand alone) de Lua.
Para máquinas Windows, uma ótima opção de instalação é a distribuição Lua for Windows (LfW). Essa distribuição é um pacote completo para Windows, incluindo não apenas o interpretador Lua com suas bibliotecas padrão mas também um editor e várias bibliotecas extras populares.
Para máquinas Linux não há uma receita pronta, dada a diversidade de distribuições de Linux. Compilar Lua em uma máquina Linux é muito simples e rápido. Algumas distribuições já vêm com Lua instalado por default. Outras oferecem pacotes prontos: por exemplo, em Ubuntu e Debian, basta instalar o pacote lua5.1, que é o interpretador com as bibliotecas padrão. Várias bibliotecas externas também são oferecidas como pacotes extras. Em qualquer caso, o interpretador independente de Lua é um programa de linha de comando, para ser executado por meio de um terminal.
Para máquinas Mac OS X, existe a opção de compilar diretamente o fonte, desde que a máquina já tenha as ferramentas de desenvolvimento em C instaladas. O processo é simples e rápido como no Linux. Outra opção é usar um gerenciador de pacotes; por exemplo, tanto o MacPorts quanto o Fink oferecem pacotes prontos para Lua.

Variáveis e tipos

Em Lua, as variáveis não têm tipos associados a elas: os tipos estão associados aos valores armazenados nas variáveis. Dessa forma, uma mesma variável pode num momento armazenar um valor de um tipo e depois passar a armazenar o valor de outro tipo (naturalmente, a variável deixa de armazenar o valor inicial). O trecho de código abaixo ilustra o uso de variáveis armazenando diferentes valores:

a = "Exemplo" -- a armazena string
b = 1.23 -- b armazena número
...
b = nil -- b armazena nil
a = 3 -- a armazena número

Os valores em Lua podem ser de oito tipos:

  • nil: o valor nil indica ausência de valor. Variáveis não inicializadas contêm o valor nil. O valor nil também é interpretado como falso numa expressão booleana;
  • boolean: valor booleano, podendo ser falso (false) ou verdadeiro (true);
  • number: valor numérico. Lua não diferencia valor inteiro de valor real; só existe um tipo para representar números;
  • string : valor cadeia de caracteres. Uma constante string pode ser delimitada por aspas duplas (”…”), aspas simples (’…’), ou duplo colchetes ( [ […] ] );
  • table: vetor associativo;
  • function: função escrita em Lua ou escrita em C e registrada em Lua;
  • userdata: dado do host, representado por um ponteiro void*;
  • thread: linha de execução, quando descrevermos o uso de co-rotinas em Lua.

Operadores e controladores de fluxo

A linguagem Lua oferece os operadores comumente encontrados em linguagens de programação. Os operadores aritméticos são os usuais: + (adição), - (subtração), * (multiplicação), / (divisão), ^ (exponenciação) e - unário (negação). Os operadores relacionais resultam num valor booleano e incluem: < (menor que), > (maior que), ⇐ (menor ou igual que), >= (maior ou igual que), == (igualdade), ~= (diferença). Os operadores lógicos servem para combinar valores booleanos e são dados por: and (e), or (ou), not (negação). Existe ainda o operador .. para concatenação de strings.


A linguagem Lua oferece os controladores de fluxo comuns às linguagens procedurais. As construções para tomada de decisão são as variantes usuais de if … then … else:

if expr then
...
end
if expr then
...
else
...
end
if expr1 then
...
elseif expr2 then
...
else
...
end

As construções para execução iterativa podem ter o seu teste no início (while) ou nofim(repeat):

while expr do
...
end
repeat
...
until expr

Lua oferece ainda a construção de laços com for. O for numérico tem a seguinte forma:

for var = expr_inicial, expr_final, expr_incremento do
...
end

Funções

Funções em Lua são valores de primeira classe. Isso significa que, como qualquer outro valor, uma função pode ser criada, armazenada em uma variável (local ou global) ou campo de tabela e passada adiante como parâmetro ou valor de retorno de uma outra função. Uma função pode receber zero ou mais valores. A lista de parâmetros é especificada da maneira usual: entre os parênteses que seguem o nome da função. Como exemplo simples (tradicional, mas útil somente para fins didáticos), consideremos a definição da função recursiva abaixo para o cálculo do fatorial de um número inteiro:

function fat (n)
   if n==0 then
      return 1
   else
      return n*fat(n-1)
   end
end

Tabelas e objetos

O tipo table representa um vetor associativo, implementado internamente com o uso de uma eficiente combinação de array e hash (tabela de dispersão). As tabelas são a única forma de estruturação de dados em Lua. Todas as estruturas de dados comumente encontradas em programação (tais como vetores, listas, filas, conjuntos e hash) podem ser eficientemente (e facilmente) implementadas com o uso de tabelas. Uma tabela em Lua é criada pela expressão { }. Se uma variável armazena um valor do tipo tabela, essa variável pode ser indexada por qualquer outro valor (exceto nil ). O valor armazenado em cada índice da tabela também pode ser de qualquer tipo (incluindo nil ). O valor associado a um índice da tabela não inicializado tem o valor nil. O trecho de código abaixo ilustra a criação de uma tabela e a atribuição de alguns campos:

local t = {} -- cria nova tabela
t[1] = 4 -- armazena 4 no índice 1
t[2] = "alo" -- armazena "alo" no índice 2
t["alo"] = 5 -- armazena 5 no índice "alo"
t[t[2]] = 0 -- armazena 0 no índice "alo" (sobrescrevendo)

Biblioteca padrão

A distribuição oficial de Lua inclui um conjunto de bibliotecas que implementam diversas funções importantes para a construção de programas. Com exceção das funções que pertencem ao que chamamos de biblioteca básica, as funções de cada biblioteca são agrupadas em tabelas. Assim, a tabela string agrupa as funções para manipulação de strings, a tabela table agrupa as funções para manipulação de tabelas e assim por diante. Listamos abaixo as bibliotecas padrão inclúidas na distribuição. O manual de referência contém uma descrição detalhada das funções oferecidas. Além da biblioteca básica, que oferece funções básicas para a programação em Lua (como print, setmetatable, pairs, que usamos acima), a distribuição inclui as seguintes bibliotecas:

  • string: Oferece funções para manipulação de strings;
  • math: Oferece funções matemáticas;
  • table: Oferece funções para manipulação de tabelas;
  • io: Oferece funções para operações de entrada e saída;
  • os: Oferece funções relacionadas ao sistema operacional;
  • debug: Oferece funções para depuração de códigos Lua.

Co-rotinas

Co-rotinas são um poderoso mecanismo de programação para jogos. Uma co-rotina é semelhante a um thread num sistema de multithreading, no sentido de que temos uma linha de execução com seu próprio ambiente local (pilha de execução) compartilhando o ambiente global com outras corotinas. A grande diferença entre uma co-rotina e uma função ´e que a execução de uma co-rotina pode ser suspensa e retomada posteriormente (no ponto em que foi suspensa). A diferença entre co-rotinas e threads é que, conceitualmente, diferentes threads executam simultaneamente, enquanto que num sistema com co-rotinas, apenas uma co-rotina executa por vez. As funções que manipulam co-rotinas estão agrupadas na tabela coroutine. Criamos uma co-rotina passando uma função (em geral, anômina) para a função de criação, que retorna um valor do tipo thread:

local c = coroutine.create(function () ... end)
print(type(c)) --> "thread"

Onde a Lua é usada atualmente?

Atualmente a Lua tem uma vasta área de utilização abaixo podemos ter uma ideia de onde a Lua é utilizada com alguns exemplos mais populares dos muitos existentes:

  • Acessibilidade: Dolphin Computer Access;
  • Educação: Celestia;
  • Simuladores de vôo: DCS: Black Shark;
  • Mecanismos de jogos (engine): Enigma Game Engine;
  • Jogos: Allods Online, Angry Birds, Civilization V, Crysis, Far Cry, SimCity 4, World of Warcraft;
  • IDE's: Crank Storyboard Suite, Lua Player;
  • Processamento de Imagem: Adobe Photoshop Lightroom, GIMP;
  • Internet: Apache HTTP Server, Nmap, Wireshark;
  • Variados: Asterisk: Telecom PBX, Girder, IOS Software Development Kit;
  • Multimídia: Aqualung, Digital Fusion, Giggle;
  • Sistemas operacionais e gerenciadores de janelas: Awesome Windows Manager, Lua OS.
  • Gerenciadores de pacotes: Alpine Linux, Clyde;
  • Editores de texto: CodeMAX, FXiTe, Gnu Zile;
  • Gerenciamento de Banco de Dados Relacional: MySQL Proxy, MySQL Workbench, PL/Lua (PostgreSQL);
  • Robótica: Crazy Ivan Robot, V-REP.

Comentários finais

Neste texto procuramos mostrar sucintamente todos os atributos da linguagem de programação Lua, história, características, sintaxe, como usá-la, onde é usada, para que se consiga mostrar a todos com clareza os aspectos da linguagem.

Referências

 
lua-1-trabalho.txt · Last modified: 2012/03/18 17:17 by clp · [Old revisions]