• Sonuç bulunamadı

Yadsıma: Aile üyelerinde en sık kullanılan savunmadır Baba olayı “seks eğitimi” olarak savunabilir, anne ise kocası ile ilişkisini bozabileceği için reddedip görmezden

A Figura 5.24 mostra a estrutura básica das classes para a representação em memória de expressões. O mesmo recurso de fornecer uma classe básica a partir da qual as classes de expressão derivem indiretamente por meio das classes BasicExpression e ExpressionConstructor é utilizado.

As expressões básicas são os literais,a expressão self e a expressão undef, apresentados na Figura 5.25. Estas sempre guram como folhas em uma árvore que representa uma expressão. Os construtores de expressão são apresentados na Figura 5.26. Constituem este grupo os operadores unários, os operadores binários, as chamadas a funções, os agregados, os alia-

para código C++. A Figura 5.32 apresenta como as expressões mais simples são traduzidas. A tradução de um literal resulta na declaração de um valor do tipo do literal. A expressão self é traduzido para uma chamada ao método que retorna o nome do agente, ao passo que undef é mapeado para o valor NULL. Um alias é traduzido para a chamada à variável associada ao alias, obtendo o seu valor. Um operador unário segue o seguinte padrão na tradução: primeiro o seu operando é avaliado, e em seguida o operador propriamente dito é aplicado ao operando. A tradução de um operador binário resulta na avaliação do primeiro operando, seguido pela avaliação do segundo operando. De posse dos valores dos dois operandos, o operador é aplicado. Uma chamada a uma função é traduzida para a avaliação de cada parâmetro atual, seguida da chamada ao método que está associado à função. Note que a informação se a passagem é por valor ou por referência está na declaração da função, e não em sua chamada. O literal de um agregado é traduzido para a seguinte seqüência de comandos: primeiramente, a expressão de cada componenente é avaliada. Em seguida, o literal do agregado é declarado, e cada componente é adicionado. A projeção de uma tupla é traduzida primeiramente para a avaliação da expressão que resulta na tupla. Em seguida, uma variável com o tipo do i-ésimo componente projetado é declarada, e esta recebe a projeção do i-ésimo componente.

Dando continuidade, a Figura 5.33 apresenta mais alguns exemplos de tradução de ex- pressões. Uma expressão condicional if exp é traduzida de forma semelhante à tradução de uma regra conditional. A diferença é que neste caso existe um cuidado extra com a obtenção do valor da expressão if exp. Inicialmente, é criada uma variável com o tipo de retorno da expressão condicional. Em seguida, a guarda é avaliada, e então esta guarda é testada em um comando if de C++. A expressão correspondente ao braço then da expressão condicional é avaliada dentro do bloco correspondente ao then do comando if. No nal da avaliação, o resultado se torna disponível externamente por meio da atribuição deste à variável declarada externamente com o tipo da expressão condicional. A geração de código para o braço else é análoga.

A tradução da expressão let exp acontece da seguinte forma. Inicialmente, é criada uma variável com o tipo de retorno da expressão let exp para conter o resultado da expressão como um todo. Em seguida, é criado um bloco C++ e dentro dele é avaliada a expressão que denota o valor associado ao nome dado, e então esta associação é feita. Em seguida, o código da avaliação da expressão principal é gerado, tendo acesso ao valor denotado pela expressão associada ao nome por meio do alias. O término da avaliação da expressão principal do let exp é seguido pela atribuição do valor resultante à variável criada para conter o valor da expressão como um todo. O fechamento do bloco C++ determina o m do escopo da alias.

A Figura 5.34 apresenta um exemplo da tradução de uma expressão case exp. Inicialmente, é criada uma variável com o tipo de retorno da expressão case exp para conter o resultado da

Figura 5.29: Diagrama de classes: chamadas de função.

Figura 5.31: Diagrama de classes: agregados.

expressão como um todo. Em seguida, a guarda é avaliada, e o resultado de sua avaliação é utilizado para determinar qual é a alternativa escolhida. As alternativas são traduzidas para comandos if em C++, devidamente entremeados com comandos else que garantem a exclusão mútua na escolha das alternativas. Dentro do bloco correspondente a cada alternativa, o código para a avaliação da expressão é gerado, e o resultado desta avaliação é diponibilizado externamente por meio da atribuição à variável declarada para conter o resultado da expressão case exp como um todo. Além disso, é gerado também um bloco else que corresponde ao caso em que nenhuma alternativa foi escolhida.

A Figura 5.35 apresenta um exemplo da tradução de uma expressão with exp. A tradução da expressão with exp é semelhante à tradução da expressão case exp, porém duas diferenças devem ser ressaltadas. A primeira é que a comparação para escolha da alternativa a ser exe- cutada se baseia não no valor da expressão avaliada, mas sim no seu tipo. Esta comparação é feita por meio de uma chamada à função typeEquivalent, desenvolvida como parte da biblioteca de runtime, e que se utiliza das funcionalidades disponibilizadas pela RTTI (Real Time Type Information) de C++. O critério de comparação é, via de regra, a comparação estrutural. A exceção ca por conta dos tipos construídos por meio de node, que são comparados de acordo com o seu rótulo. A segunda diferença é que, em cada alternativa, o primeiro código gerado é o typecast da expressão avaliada para o tipo encontrado e sua associação com o identicador dado. Desta forma, o valor da expressão se torna disponível dentro da alternativa.