CONSTRUÇÃO DE UM COMPILADOR PARA LÓGICA GAL

Propaganda
CONSTRUÇÃO DE UM COMPILADOR PARA LÓGICA GAL UTILIZANDO
JAVACC
1
Lucas Ismaily B. Freitas, 2 Prof. Davi Romero de Vasconcelos (orientador)
1,2
Universidade Federal do Ceará, Quixadá, Ceará, Brasil
[email protected], [email protected]
RESUMO: Este trabalho apresenta a construção de um compilador (análise léxica,
sintática e construção de objetos) para a Lógica Modal de Primeira-Ordem GAL
(Game Analysis Logic) (VASCONCELOS, 2007). Este compilador recebe como entrada
uma fórmula em GAL e retorna um objeto Java do framework GALV (Game Analysis
Logic Verifier)(GALV, 2011). Usamos o framework GALV (Game Analysis Logic
Verifier), pois ele implementa um verificador de modelos para Lógica GAL. No GALV,
as fórmulas GAL utilizadas para analisar problemas são representadas como objetos
de classes Java . Fizemos uso também dos conhecimentos de gramáticas livre de
contexto para representar a Lógica como uma gramática e utilizamos também, a
tecnologia JavaCC(Java Compiler Compiler)(JAVACC, 2011) para a construção do
compilador a partir da gramática gerada.
1. INTRODUÇÃO
Existem muitas possibilidades de resolução de problemas da vida real com teoria
dos jogos. Várias situações em que ocorrem conflitos de interesses geralmente podem
ser modeladas com algum tipo de jogo. Uma das formas é utilizando Lógicas como
ferramentas, mais especificamente, o framework GALV. O framework GALV é
desenvolvido em Java SE, e tem implementado um verificador de modelos para a lógica
GAL e vários aspectos de teoria dos jogos, nele as fórmulas em GAL são representadas
como um conjunto de objetos de classes Java.
Em verificação de modelos (model checking) (CLARKE; GRUMBERG;
PELED, 1999), o sistema e a propriedade a ser validada são representados,
respectivamente, como um modelo, geralmente finito, e uma fórmula da lógica, neste
caso uma fórmula em lógica GAL, que pode ser recebida como entrada pelo usuário
(uma string de entrada). A busca por procedimentos eficientes que decidam se uma
fórmula δ, que representa uma propriedade do sistema, é satisfeita (|=) na estrutura G,
geralmente finita, que representa o sistema, é fator chave em verificação de modelos.
Um enunciado para o problema de verificação de modelos é introduzido, segundo
(VASCONCELOS, 2007), como: G |= δ
Por ser bastante dispendioso fazer análise léxica e sintática das fórmulas GAL
recebidas como entradas para o verificador de modelos, um compilador próprio da
lógica que gera um objeto instanciado (Formula GAL no GALV) proporciona um ganho
de tempo precioso para o projeto.
Para construção deste compilador é necessário construirmos uma gramática livre
de contexto não recursiva a esquerda, que gera a linguagem Lógica GAL. De posse da
gramática, utilizamos a tecnologia JavaCC para construção do compilador.
2. METODOLOGIA
O JavaCC requer uma Gramática Livre de Contexto sem recursão à esquerda, por tanto
devemos inicialmente modelar a Lógica GAL como uma GLC(Gramática Livre de Contexto),
aplicar algoritmos de eliminação de recursão à esquerda e em seguida utilizar o JavaCC para
fazer a análise léxica, sintática e construção os objetos.
Lógica GAL
GLC sem
recursão à
esquerda
JavaCC
Compilador
Figura 1. Sequência de passos para a construção do
compilador.
3. DISCUSSÃO E RESULTADOS
A Lógica GAL
GAL é uma lógica poli-sortida modal de primeira-ordem, chamada de Game
Analysis Logic (GAL), baseada na lógica Computation Tree Logic (CTL)
(VASCONCELOS, 2007). Utilizada para modelar e analisar problemas em teoria dos
Jogos, assim como definir propriedades dos Jogos e conceitos de racionalidades, por
exemplo, Equilíbrio de Nash.
A definição é de forma usual, ou seja, requer definição dos termos, linguagem
lógica e não lógica, para mais detalhes indicamos (VASCONCELOS, 2007).
A linguagem lógica GAL é gerada pela seguinte BNF:
Θ:= T | i | P(t1,...,tn) | t≈ t’ | (¬Θ) | (Θ→Θ) | (Θ ˄ Θ) | (Θ ˅ Θ) |
|
| [AX]Θ |
[AG]Θ | [AF]Θ | A(ΘuΔ) | [EX]Θ | [EG]Θ | [EF]Θ | E(ΘuΔ)
A interpretação dos operadores lógicos binários e unários é como na lógica
clássica, porém os operadores modais são interpretados como segue:
 [EX]Θ significa que existe um caminho tal que no próximo estado vale Θ;
 [EF]Θ significa que existe um caminho tal que no futuro vale Θ;
 [EG]Θ significa que existe um caminho tal que sempre vale Θ;
 [AX]Θ significa que para todo caminho no próximo estado vale Θ;
 [AF]Θ significa que para todo caminho no futuro vale Θ;
 [AG]Θ significa que para todo caminho sempre vale Θ;
 A(ΘuΔ) significa que para todo caminho vale Θ até que Δ;
 E(ΘuΔ) significa que existe um caminho tal que vale Θ até que Δ.
Em modo gráfico temos:
Figura 2. Representação gráfica da interpretação dos operadores modais. Fonte: VASCONCELOS, 2007.
Gramática Livre de Contexto
Uma gramática livre de contexto (GLC) é uma quádrupla <V, ∑, S, P> onde:
 ∑ é o alfabeto sobre o qual a linguagem é definida;
 V é um conjunto não vazio de símbolos não terminais;
 P é um conjunto de produções da forma A → α, onde A ∈ V e α ∈ (∑ ∪
V)*;
 S é o símbolo inicial da gramática, S ∈ V.
Um exemplo em lógica: G= <{Form}, {AND,OR}, Form, P>, em que P é:
Form -> (Form AND Form) | (Form OR Form).
Para mais detalhes sobre GLC indicamos (MENEZES, 2005).
JavaCC
JavaCC é gerador de parser Java. Inicialmente desenvolvido pela Sun, porém
hoje mantido pela Java.net. Inclui um pré-processador para geração de árvores sintáticas
(jjTree). Definição léxica e sintática em um único arquivo e sem ambiguidade (não
aceita gramática recursiva à esquerda).
Estrutura de arquivos em JavaCC
1. Opções do parser
Define as opções do parser e algumas características de desempenho e
depuração, por exemplo, a opção DEBUG_PARSER instrui o parser a registrar todas as
informações durante o parsing do arquivo.
2. Definição da classe do Parser
Este trecho define a classe do Parser. Nesta classe, podem ser definidos métodos
e variáveis auxiliares. O formato é o seguinte:
public class ParserGAL implements ParserGALConstants{
public static void main(String args[]) throws ParseException {
System.out.println("Digite sua Formula GAL:");
ParserGAL parser = new ParserGAL(System.in);
GALFormula f = null; f = parser.parserGAL();
if (f != null) {
System.out.println("O toString da Formula instanciada:");
System.out.println(f.toString()); }
Figura 3. Estrutura da classe do Parser
}
Figura 4. Definição do Parse utilizado no trabalho
3. Definição dos tokens
Serve para especificar os tipos de tokens e as expressões regulares associadas.
Esta seção serve para descrever as palavras reservadas
Operadores da Lógica GAL
TOKEN : { <T: (["a"-"z"])+> | <EX : "[EX]"> | <EU : "[EU]"> | <EF : "[EF]"> | <EG : "[EG]"> | <AF : "[AF]"> |
<AG : "[AG]"> | <AX : "[AX]"> | <AU : "[AU]"> | <Exists : "[Exists]"> | <ForAll : "[ForAll]"> |
<TRUE : "T"> | <FALSE : "F"> }
Operadores da Lógicos
TOKEN :{
}
<AND: "AND"> | <NOT: "NOT"> | <IMP: "->"> | <OR: "OR"> | <XOR: "XOR"> | <EQUALS: "=">
Figura 4. Exemplo de definição de tokens aritméticos
Operadores para expressões
TOKEN :{
<PareEsq: "("> | <ColcEsq: "["> | <ColcDir: "]"> | <PareDir: ")"> | <Virgula: ","> | <EOL: "\n">}
Figura 5. Definição das palavras reservadas utilizadas no trabalho
4. Definição das produções
Parte fundamental. Recebem
como entrada as produções da
gramática e como saída código Java.
Obedecem ao seguinte formato:
Figura 6. Estrutura das definições das
regras de produções
Um exemplo de produções no trabalho apresentado segue na Figura 7
GALFormula getFormulaGAL():{Token variavel;GALFormula form,f;}
{<EX><PareEsq>form=getFormula()<PareDir> { return new EXMC(form);}
|
<EF><PareEsq>form=getFormula()<PareDir> {return new EFMC(form);}
|
<EU><PareEsq>form=getFormula()<Virgula>f=getFormula()<PareDir>{return new EUMC(form,f);}|
<AU><PareEsq>form=getFormula()<Virgula>f=getFormula()<PareDir>{return new AUMC(form,f);}|
<EG><PareEsq>form=getFormula()<PareDir> {return new EGMC(form);}
|
<AG><PareEsq>form=getFormula()<PareDir> {return new AGMC(form);}
|
<AX><PareEsq>form=getFormula()<PareDir> {return new AXMC(form);}
|
<AF><PareEsq>form=getFormula()<PareDir> {return new AFMC(form);}
|
<Exists><ColcEsq>variavel=<T><ColcDir><PareEsq>form=getFormula()<PareDir> {
return new Exists(new Variable(variavel.image, null), form);}
|
<ForAll><ColcEsq>variavel=<T><ColcDir><PareEsq>form=getFormula()<PareDir> {
return new ForAll(new Variable(variavel.image, null),form );}
<NOT><PareEsq>form=getFormula()<PareDir> {return new NOT(form);}
|
|
form=getPropositionSymbol() {return form;}
|
<TRUE> {return new TRUE();}
|
<FALSE> {return new FALSE();}
}
Figura 7. Definições de regras no trabalho apresentado
4. CONCLUSÃO
Esperamos ter contribuído de alguma forma para modelagem e análise de
problemas usando a Lógica GAL.
O código completo do trabalho está disponível em (PARSER, 2011). Há
acréscimos que podem ser desenvolvido, por exemplo, ordem de precedência, mais
semântica, melhores mensagens de erros.
5. BIBLIOGRAFIA
VASCONCELOS, D. R. Lógica Modal de Primeira-ordem para Raciocinar sobre
Jogos. 2007. Tese (Doutorado em Informática) – Departamento de Informática,
Pontifícia Universidade Católica do Rio de Janeiro, Rio de Janeiro, 2007.
JavaCC Home(JAVACC). Disponível em: < http://javacc.java.net/ >. Acesso em: 9 de
agosto de 2011.
MENEZES, Paulo F. B.; Linguagens Formais e Autômatos. 5. Ed. Porto Alegre:
Sagra Luzzatto, 2005.
GALV. Disponível em: <http://www.tecmf.inf.pucrio.br/DaviRomero>. Acesso em 9
de agosto de 2011.
ALMEIDA, Pedro Q. de. Compiladores. Faculdade de Ciências e Tecnologia da
Universidade
de
Coimbra,
2005.
Disponível
em:
<
http://www.mat.uc.pt/~pedro/lectivos/compiladores/ >. Acesso em: 9 agosto de 2011.
Compilador
Lógica
GAL
(PARSER).
Disponível
em:
<http://www.megaupload.com/?d=YRRPPBKZ>. Acesso em: 09 de agosto de 2011.
E. M. Clarke, O. Grumberg, and D. A. Peled. Model Checking. MIT Press, 1999.
Download