A apresentação está carregando. Por favor, espere

A apresentação está carregando. Por favor, espere

Aula sobre JavaCC Parsing Tarciana Dias tds@cin.ufpe.br Abril 2013.

Apresentações semelhantes


Apresentação em tema: "Aula sobre JavaCC Parsing Tarciana Dias tds@cin.ufpe.br Abril 2013."— Transcrição da apresentação:

1 Aula sobre JavaCC Parsing Tarciana Dias Abril 2013

2 Roteiro Sobre o JavaCC – forma de especificação das gramáticas
Instalando o plugin do JavaCC no eclipse Análise da gramática default gerada pelo JavaCC Analisando a linguagem de expressões 1 Revisando conceitos básicos de gramáticas LL Aplicando os conceiros na gramática do exp1 Referências

3 Exemplo 1 Gramática Start := NUMBER ( “+” NUMBER )

4 Classe do parser parser = new Adder(new FileInputStream("input.txt"));
options { STATIC = false ; } PARSER BEGIN(Adder) public class Adder { static void main( String[] args ) throws ParseException, TokenMgrError { Adder parser = null; try { parser = new Adder(new FileInputStream("input.txt")); } catch (FileNotFoundException e) { // TODO Auto-generated catch block e.printStackTrace(); System.out.println(parser.start());} PARSER END(Adder)

5 Analisador léxico SKIP : { ” ” } SKIP : { ”\n” | ”\r” | ”\r\n” }
TOKEN : { < PLUS : ”+” > } TOKEN : { < NUMBER : ([”0”-”9”])+ > }

6 Gramática “EBNF” void Start() : {} { <NUMBER> ( <PLUS> )*
<EOF> }

7 Possiveis saidas Entrada válida: 1 + 5
Token inválido: 1 – 3 ( Exceção) Erro sintático: (Exceção)

8 Código gerado final public void start() throws ParseException {
jj_consume_token(NUMBER); label_1: while (true) { switch ((jj_ntk==-1)? jj_ntk() : jj_ntk) { case PLUS: ;break; default: jj_la1[0] = jj_gen; break label_1; } jj_consume_token(PLUS); jj_consume_token(0); }

9 Adicionando ações int Start() throws NumberFormatException : {
Token t ; int i ; int value ; } { t = <NUMBER> { i = Integer.parseInt( t.image ) ; } { value = i ; } (<PLUS> { value += i ; } )* <EOF> { return value ; }}

10 Roteiro Sobre o JavaCC – forma de especificação das gramáticas
Instalando o plugin do JavaCC no eclipse Análise da gramática default gerada pelo JavaCC Analisando a linguagem de expressões 1 Revisando conceitos básicos de gramáticas LL Aplicando os conceiros na gramática do exp1 Referências

11 Plugin Eclipse Baixar o plugin: Pagina do plugin:
Para atualizar o eclipse com o plugin: Pegar a pasta ...\sf.eclipse.javacc plugin\plugins\sf.eclipse.javacc_ e copiá-la para o caminho do eclipse ...\eclipse\plugins Fazer o mesmo para a pasta ...\sf.eclipse.javacc plugin\features\sf.eclipse.javacc.feature_ só que para o caminho ...\eclipse\features

12 Quick start plugin eclipse
Criar um projeto Java no eclipse Criar uma pasta foo submissa à pasta do projeto Em seguida, criar um novo projeto só que selecionando a opção Other, escolhendo a pasta JavaCC e a opção JavaCCTemplateFile, conforme mostrado a seguir: New->Other, ir na opção javaCC-> JavaCC Template File

13 Quick start plugin eclipse [2]

14 Quick start plugin eclipse [3]
Ao clicar em Next, a tela seguinte aparece. Observe que se deve indicar a gramática utilizada como referência. No caso default, ele utiliza MyNewGrammar.jj Mas podemos colocar uma das gramáticas disponíveis na página da disciplina /~in101 e vistas até então (iremos fazer depois): Expressoes1.jj ou Expressoes2.jj ou Funcional1.jj

15 Quick start plugin eclipse [4]

16 Quick start plugin eclipse [5]
Após escolhida a gramática, clica-se em Finish:

17 Arquivos gerados EG1 EG1Constants EG1TokenManager MyNewGrammar.jj
ParserException SimpleCharStream Token TokenMgrError Parei na página 7 do tutorial.

18 Roteiro Sobre o JavaCC – forma de especificação das gramáticas
Instalando o plugin do JavaCC no eclipse Análise da gramática default gerada pelo JavaCC Analisando a linguagem de expressões 1 Revisando conceitos básicos de gramáticas LL Aplicando os conceiros na gramática do exp1 Referências

19 Outro Exemplo Gramática Vide MyNewGrammar.jj

20 Roteiro Sobre o JavaCC – forma de especificação das gramáticas
Instalando o plugin do JavaCC no eclipse Análise da gramática default gerada pelo JavaCC Analisando a linguagem de expressões 1 Revisando conceitos básicos de gramáticas LL Aplicando os conceiros na gramática do exp1 Referências

21 Vamos agora analisar a gramática da linguagem de expressões 1
Antes disso, vamos revisar as técnicas de fatorar uma gramática à esquerda e eliminar recursões à esquerda

22 Conceitos Básicos Transformações de Gramática
Fatoração à esquerda Ex;: XY | XZ equivale à X (Y | Z) single-Command ::= V-name := Expression | if Expression then single-Command else single-Command ( ε | else single-Command)

23 Conceitos Básicos Transformações de Gramática
Eliminação de recursão à esquerda N ::= X | NY, onde N é um símbolo não-terminal e X e Y são REs estendidas. Esta produção é recursiva à esquerda. N ::= X(Y)* Substituindo por uma regra EBNF equivalente

24 Eliminando recursão à esquerda
Conceitos Básicos Transformações de Gramática Identifier ::= Letter | Identifier Letter | Identifier Digit | Identifier (Letter | Digit) Identifier ::= Letter (Letter | Digit)* Fatorando à esquerda Eliminando recursão à esquerda

25 Conceitos Básicos A necessidade da eliminação de recursão à esquerda é melhor entendida depois que se vai usar a abordagem top-down;

26 Estratégias de Parsing
Objetivo Reconhecimento de uma string de entrada (seqüência de tokens) e decisão se esta é ou não uma sentença de G Determinação de sua estrutura de frases (pode ser representada por uma árvore sintática) Gramática não ambígua: cada sentença tem exatamente uma syntax tree Top-Down Examina os símbolos terminais da esquerda para a direita Forma a ST (syntax tree) de cima para baixo Parsing ok: string de entrada totalmente conectada à ST L(eft-to-right) L(eft-most-derivation) => LL Bottom-Up Forma a ST (syntax tree) de baixo (nós terminais) para cima(nó raiz) Parsing ok: string de entrada reduzida a uma S-tree S(imple) L(eft-to-right) R(ight-most-derivation) => SLR L(eft-to-right) R(ight-most-derivation) => LR L(ook) A(head) L(eft-to-right) R(ight-most-derivation) => LALR ESTUDAR ESSE SLIDE NO LIVRO DO AHOA

27 Aqui ele não poderia ter escolhido um Subject?
Estratégia Bottom-Up Exemplo: Sentence ::= Subject Verb Object Subject ::= I | a Noun | the Noun Object ::= me | a Noun | the Noun Noun ::= cat | mat | rat Verb ::= like | is | see | sees the cat sees a rat . Sentence Aqui ele não poderia ter escolhido um Subject? Object Subject O que diferencia ele ter escolhido um Object e não um Subject? O fato de antes ele já ter um Object e um Verb. Assim, parsers seguindo essa estratégia devem levar em conta os passos do parsing anteriores. Verb Noun Noun

28 Estratégia Top-Down the cat sees a rat .
Exemplo: Sentence ::= Subject Verb Object Subject ::= I | a Noun | the Noun Object ::= me | a Noun | the Noun Noun ::= cat | mat | rat Verb ::= like | is | see | sees the cat sees a rat . Sentence Object Subject O que diferencia ele ter escolhido um Object e não um Subject? O fato de antes ele já ter um Object e um Verb. Assim, parsers seguindo essa estratégia devem levar em conta os passos do parsing anteriores. Verb Noun Noun

29 Estratégias de Parsing
Qual estratégia de parsing devemos usar? Isso vai depender do tipo de gramática ! Sempre é necessário escolher qual regra de produção aplicar Isto é feito de acordo com o algoritmo de Parsing Recursive Descent é um algoritmo de parsing top-down Consiste de um grupo de métodos parseN, um para cada símbolo não-terminal N de G. Estes métodos cooperam para fazer o parse das sentenças completas parseSentence parseSubject parseVerb parseObject parseNoun parseNoun the cat sees a rat .

30 Gramáticas LL(1) Deve-se expressar a gramática em EBNF, com uma regra de produção simples para cada símbolo não-terminal, e realizar as transformações de gramática necessárias, por exemplo, sempre eliminar recursão à esquerda e fatorizar à esquerda sempre que possível Gramáticas LL(1): Se a gramática contém X | Y, starters[[ X ]] e starters[[ Y ]] devem ser disjuntos Se a gramática contém X* , starters[[ X ]] deve ser disjunto do conjunto de tokens que podem seguir X* Na prática quase toda gramática de uma linguagem de programação pode ser transformada em LL(1), sem mudar a linguagem que a gramática gera Recursive-descent parsing é somente adequado para gramáticas LL(1) Em geral, o projetista da linguagem projeta a sua sintaxe para ser adequada à um parsing recursive-descent.

31 Gramáticas não-LL(1) Exemplo de uma Gramáticas não LL(1):
Program ::= single-Command Command ::= single-Command (; single-Command)* V-name ::= Identifier single-Command ::= V-name := Expression | Identifier ( Expression ) | if Expression then single-Command else single-Command Expression ::= primary-Expression (Operator primary-Expression)* primary-Expression ::= Integer-Literal | Identifier

32 Uma simples fatoração à esquerda resolve o problema!
Gramáticas não-LL(1) Desenvolvimento do método parseSingleCommand: Uma simples fatoração à esquerda resolve o problema! private void parseSingleCommand(){ switch(currentToken.kind){ case Token.IDENTIFIER: { parseVname(); accept(Token.BECOMES); parseExpression(); } break; parseIdentifier (); accept(Token.LPAREN); accept(Token.RPAREN); V-name ::= Identifier single-Command ::= V-name := Expression | Identifier ( Expression ) | … single-Command ::= Identifier (:= Expression | ( Expression ) )

33 Gramáticas não-LL(1) Exemplo de uma Gramáticas não LL(1): …
Aqui, starters[[ ;Declaration ]] = {;} e o conjunto de terminais que seguem (; Declaration)* neste contexto também é {;} Como não são disjuntos, então a gramática não é LL(1) Block::= begin Declaration (; Declaration)* ; Command end Declaration ::= integer Identifier (, Identifier)* Como resolver? private void parseBlock(){ accept(Token.BEGIN){ parseDeclaration(); while (currentToken.kind == Token.SEMICOLON) acceptIt(); } accept(Token.SEMICOLON); parseCommand(); accept(Token.END); Block::= begin Declaration ; (Declaration;)* Command end Assumindo que starters[[(Declaration)*]] é disjunto de starters[[Command]]

34 Recursive Descent Parser
Algoritmo de parsing para gramáticas LL Visão geral Para cada produção N, crie um método parseN Crie uma classe parser com um atributo currentToken E os métodos parseN E os métodos auxiliares: accept e acceptIt E um método público parse que chama parseS O código de cada método parseN depende da produção N A árvore é dada implicitamente pela chamada dos métodos Pode ser criada explicitamente

35 Roteiro Sobre o JavaCC – forma de especificação das gramáticas
Instalando o plugin do JavaCC no eclipse Análise da gramática default gerada pelo JavaCC Analisando a linguagem de expressões 1 Revisando conceitos básicos de gramáticas LL Aplicando os conceiros na gramática do exp1 Referências

36 Criando a estrutura para a linguagem exp1
Baixar a gramática Expressoes1.jj contida em Observar no início do arquivo que: PARSER_BEGIN(Exp1Parser) package plp.expressions1.parser; import plp.expressions1.*; import plp.expressions1.expression.*; import plp.expressions1.util.*; Logo devemos criar o projeto java seguindo a estrutura plp.expressions1 etc etc !

37 Criando a estrutura para a linguagem exp1
Criar um projeto java comum Em seguida criar um pacote chamado plp e em seguida um chamado expressions1, submisso à plp Em seguida criar uma pasta/pacote parser dentro de expressions1 Selecione a pasta parser e repita o processo anterior de criar um projeto JavaCC

38 Criando a estrutura para a linguagem exp1
File-> New->Other, ir na opção javaCC-> JavaCC Template File

39 Criando a estrutura para a linguagem exp1

40 Criando a estrutura para a linguagem exp1
Vá até a pasta onde os arquivos foram gerados, pasta parser, apague todos e coloque na pasta apenas o arquivo da gramática Expressoes1.jj Você vai notar que o eclipse gera todos os arquivos novamente, de forma automática, só que agora tendo como referência a nova gramática.

41 Criando a estrutura para a linguagem exp1
Dois dos arquivos gerados, Exp1Parser e Exp1ParserTokenManager apresentarão erros de compilação. Isto porque estão faltando ainda algumas classes básicas como por exemplo Valor, ValorInteiro, etc, mencionadas no arquivo .jj por isso referenciadas pelo Exp1Parser.java gerado pelo JavaCC. Além desta a classe Programa também é referenciada.

42 Criando a estrutura para a linguagem exp1
Baixar da página da disciplina as classe listadas abaixo

43 Criando a estrutura para a linguagem exp1
Criar o pacote expression no mesmo nível do pacote parser e colocar as classes listadas anteriormente no pacote expression Ainda, classe Programa também é referenciada nas classes geradas. Baixar a mesma na página da disciplina e colocá-la no pacote expressions1 Ainda, as classes Tipo e TipoPrimitivo também são referenciadas. Baixá-las e colocá-las dentro do pacote util, a ser criado no mesmo nível do pacote parser e do pacote expression.

44 Referências WATT, D.; BROWN, D. Programming Language Processors in Java. Capítulo 4 Foco maior na abordagem LL Site do plugin JavaCC para eclipse: Tutorial JavaCC: Site do JavaCC:

45 Aula sobre JavaCC Parsing Tarciana Dias Abril 2013


Carregar ppt "Aula sobre JavaCC Parsing Tarciana Dias tds@cin.ufpe.br Abril 2013."

Apresentações semelhantes


Anúncios Google