valiação de Expressões valiação de Expressões - Como efetuar o cálculo de uma expressão em um computador? Exemplo: / B C D + E Regras usuais da matemática. Os parênteses alteram a ordem das expressões: O que dificulta a avaliação das expressões: 1º - a existência de prioridades diferentes. Exemplo: +BC 2º - a existência de parênteses Exemplo: B+C Jan Lukasienwicz conseguiu criar uma representação para expressões onde não existem prioridades e nem a necessidade de uso dos parênteses. Notação Polonesa Para somar dois números normalmente escrevemos +B, entretanto existem três formas: Na NPR: Infixa: +B Prefixa: +B Notação Polonesa Posfixa: B+ Notação Polonesa Reversa Cada operador aparece imediatamente após os valores que ele deve operar. ordem que o operador aparece é a mesma que ele deve ser efetuado. Não há necessidade do uso de parênteses. Exemplos: Notação Infixa Normal +BC B+C +B/C-D +B/C-DE Notação Posfixa BC+ BC+ B+CD-/ B+CD-/E Página 1
valiação de Expressões Conversão de Expressões Infixa em Posfixa: Parentetizar completamente a expressão definir a ordem de avaliação; Varrer a expressão da esquerda para a direita e, para cada símbolo: a. Se for parêntese de abertura, ignorar; b. Se for operando, copiá-lo para a expressão posfixa saída; c. Se for operador, fazê-lo aguardar; d. Se for parêntese de fechamento, copiar o último operador acessado. Conversão da Expressão +BC-D: 1º Etapa: Parentetização a + B C D efetua multiplicação b + B C D efetua adição c + B C D efetua subtração 2º Etapa: Varredura Símbolo dição ignora ignora copia + aguarda ignora B copia aguarda C copia remover remove aguarda D copia remove Pilha P:[,+] P:[,+] P:[ ] P:[ ] Saída B B B C B C B C + B C + B C + D B C + D Exercícios 1. B D C Etapa 1: B D C B D C Etapa 2: BDC Página 2
valiação de Expressões 2. B + C D / E + F Etapa 1: B + C D / E + F Etapa 2: B C D E F + / + function NprE:String:String; var P:Pilha; S:String; i:integer; InitP; S:= ; for i:=1 to lengthe do case E[i] of.. Z : S :=S+E[i]; {copia} +,,, / : PushP,E[i]; {aguarda} : S := S + PopP; {remove} Npr := S; lgoritmo de Conversão Infixa para Posfixa: Fundamentos para criação de algoritmos - ordem dos operandos não é alterada quando a expressão é convertida. - Os operadores devem mudar de ordem. - O que determina a posição do operador na posfixa é a prioridade que ele possui na infixa os de maior procedência aparecem primeiro. - Quando um operador é encontrado no processo de varredura, ele de aguardar até que apareça outro operador com prioridade menor ou igual a dele, somente então ele poderá ser copiado na saída. - Quando um parêntese de abertura é encontrado no processo de varredura, ele deve ser imediatamente empilhado. Uma vez empilhado, sua ordem de prioridade deve ser a menor possível para não influenciar o resultado. Página 3
valiação de Expressões Ordem de Prioridades na tualização da Expressão: function PrioS:char : integer; case S of : Prio := 1; +, : Prio := 2;, / : Prio := 3; Operador Prioridade 1 + 2 / 3 O Processo de conversão infixa para posfixa pode ser efetuado da seguinte forma: Inicie com uma pilha vazia; Realize uma varredura na expressão infixa, copiando todos os identificadores encontrados diretamente para a expressão de saída. a o encontrar um operador: 1. Enquanto a pilha não estiver vazia e houver no seu topo um operador com prioridade maior ou igual ao encontrado, desempilhe o operador e copie-o na saída; 2. Empilhe o operador encontrado; b o encontrar um parêntese de abertura, empilhe-o; c o encontrar um parêntese de fechamento, remova um símbolo da pilha e copieo na saída, até que seja desempilhado o parêntese de abertura correspondente. o final da varredura, esvazie a pilha, movendo os símbolos desempilhados para a saída. Veja o funcionamento da versão final do algoritmo na conversão da expressão B+C/D: Página 4
valiação de Expressões Símbolo ção Pilha Saída B + C / D Pilha vazia, empilha Sempre deve ser empilhado Prioridade maior, empilha Desempilha até achar Prioridade igual, desempilha Final, esvazia pilha P:[] P:[,] P:[,] P:[+,,] P:[+,,] P:[] P:[/] P:[/] B B B C B C + B C + B C + D B C + D / function PosfixaE:string : string; var P : Pilha; S : string; i : integer; x : char; InitP; S:= ; for I:=1 to lengthe do case E[i] of.. Z : S := S + E[I]; +.. -,.. / : while not IsEmptyP and PrioTopP>=PrioE[i] do S := S + PopP; PushP, E[i]; : PushP, E[i]; : while TopP<> do S := S + PopP; x:= PopP; while not IsEmptyP do S := S + PopP; Posfixa := S; valiando uma Expressão Posfixa: Percorrendo uma expressão posfixa da esquerda para a direita, ao encontrarmos um operador, sabemos que ele deve operar as duas últimas variáveis encontradas, ou seja, as duas últimas serão as primeiras a serem processadas. Página 5
valiação de Expressões Seja a expressão: B+CD-/E Supondo =7, B=3, C=6, D=4 e E=9 Podemos proceder da seguinte maneira: Iniciamos com uma pilha vazia; Varremos a expressão e, para cada elemento encontrado, fazemos: a Se for operando, então empilhar seu valor; b Se for operador, então desempilhar os dois últimos valores, efetuar a operação com eles e empilhar de volta o resultado obtido; No final do processo, o resultado da avaliação estará no topo da pilha. nalise o funcionamento do algoritmo de conversão no exemplo a seguir: Expressão Elemento ção Pilha B+CD-/E B+CD-/E +CD-/E CD-/E D-/E -/E /E E B + C D - / E Empilha valor de Empilha valor de B Desempilha y=3 Desempilha x=7 Empilha x+y Empilha valor de C Empilha valor de D Desempilha y=4 Desempilha x=6 Empilha x-y Desempilha y=2 Desempilha x=10 Empilha x/y Empilha valor de E Desempilha y=9 Desempilha x=5 Empilha xy P:[7] P:[3,7] P:[7] P:[10] P:[6,10] P:[4,6,10] P:[6,10] P:[10] P:[2,10] P:[10] P:[5] P:[9,5] P:[5] P:[45] Implementação da NPR: Em Pascal é possível implementar um vetor cujo índice é um caracter. Exemplo: Página 6
valiação de Expressões var V = rray[.. Z ] of Real; Dessa forma, os elementos do vetor V poderão ser acessados conforme sugere a figura: Representação interna das variáveis B C D E F... Z V: 7 3 6 4 9?...? Usando um vetor desse tipo é possível criar uma rotina para receber os valores de uma expressão, conforme a seguir: procedure tribuivar V:Valores; var N:char; Writeln Digite. para finalizar... ; repeat write Nome: ; readlnn; if N in [.. Z ] then write Valor: ; readlnv[n]; until N =. ; Página 7