• Nenhum resultado encontrado

RAPHAEL CHYPRIADES JUNQUEIRA AMARANTE DE EQUAÇÕES DE ONDA REPRESENTADAS EM UMA DSL ATRAVÉS DO MÉTODO DE DIFERENÇAS FINITAS

N/A
N/A
Protected

Academic year: 2021

Share "RAPHAEL CHYPRIADES JUNQUEIRA AMARANTE DE EQUAÇÕES DE ONDA REPRESENTADAS EM UMA DSL ATRAVÉS DO MÉTODO DE DIFERENÇAS FINITAS"

Copied!
54
0
0

Texto

(1)

GERAC

¸ ˜

AO DE C ´

ODIGO C PARA A RESOLUC

¸ ˜

AO

DE EQUAC

¸ ˜

OES DE ONDA REPRESENTADAS

EM UMA DSL ATRAV´

ES DO M´

ETODO DE

DIFERENC

¸ AS FINITAS

S˜ao Paulo 2020

(2)

GERAC

¸ ˜

AO DE C ´

ODIGO C PARA A RESOLUC

¸ ˜

AO

DE EQUAC

¸ ˜

OES DE ONDA REPRESENTADAS

EM UMA DSL ATRAV´

ES DO M´

ETODO DE

DIFERENC

¸ AS FINITAS

Trabalho apresentado `a Escola Polit´ecnica da Universidade de S˜ao Paulo para ob-ten¸c˜ao do T´ıtulo de Engenheiro Eletricista com ˆenfase em Computa¸c˜ao.

S˜ao Paulo 2020

(3)

GERAC

¸ ˜

AO DE C ´

ODIGO C PARA A RESOLUC

¸ ˜

AO

DE EQUAC

¸ ˜

OES DE ONDA REPRESENTADAS

EM UMA DSL ATRAV´

ES DO M´

ETODO DE

DIFERENC

¸ AS FINITAS

Trabalho apresentado `a Escola Polit´ecnica da Universidade de S˜ao Paulo para ob-ten¸c˜ao do T´ıtulo de Engenheiro Eletricista com ˆenfase em Computa¸c˜ao.

Orientador:

Edson Satoshi Gomi

Co-orientador:

Hermes Senger

S˜ao Paulo 2020

(4)

Catalogação-na-publicação

Amarante, Raphael

Geração de código C para a resolução de equações de onda representadas em uma DSL através do método de diferenças finitas / R. Amarante -- São Paulo, 2020.

51 p.

Trabalho de Formatura - Escola Politécnica da Universidade de São Paulo. Departamento de Engenharia de Computação e Sistemas Digitais. 1.GERAÇÃO DE CÓDIGO 2.EQUAÇÕES DA ONDA 3.MÉTODO DE DIFERENÇAS FINITAS 4.PYTHON 5.C (LINGUAGEM DE PROGRAMAÇÃO) I.Universidade de São Paulo. Escola Politécnica. Departamento de

(5)

Este projeto est´a inserido em um contexto de imageamento s´ısmico por invers˜ao de ondas ac´usticas, um problema de alto custo computacional que envolve a resolu¸c˜ao de equa¸c˜oes de onda. Seu objetivo central ´e a gera¸c˜ao de um c´odigo C que seja o algoritmo de resolu¸c˜ao de uma equa¸c˜ao diferencial parcial, e que tem por base o m´etodo de diferen¸cas finitas.

Para que o problema possa ser formalizado em alto n´ıvel, a equa¸c˜ao de onda ´e re-presentada em uma Domais-Specific Language que permite escrever a equa¸c˜ao de forma simb´olica, lhe conferindo simplicidade e concis˜ao. Al´em disso, com essa equa¸c˜ao se cria um estˆencil que usa o m´etodo das diferen¸cas finitas para calcular os valores num´ericos que a satisfazem. Em seguida, a express˜ao de alto n´ıvel do estˆencil ´e traduzida em uma express˜ao de baixo n´ıvel, ou seja, a express˜ao simb´olica ´e transformada em uma express˜ao de indexamento expl´ıcito que permite acessar posi¸c˜oes de um vetor que representa o pro-blema.

Assim, as realiza¸c˜oes deste projeto foram a cria¸c˜ao de um analisador sint´atico que traduz as express˜oes de alto para baixo n´ıvel, e a gera¸c˜ao de um c´odigo C que cont´em o algoritmo de solu¸c˜ao para a equa¸c˜ao diferencial parcial que descreve o problema. Tais resultados podem ser usados em projetos de imageamento s´ısmico, e o projeto em si pode ser continuado e evolu´ıdo de modo a garantir sua opera¸c˜ao com equa¸c˜oes mais complexas e de modo a possibilitar seu funcionamento com uma maior abrangˆencia de problemas.

Palavras-Chave – Domain-Specific Language, equa¸c˜ao diferencial parcial, m´etodo de diferen¸cas finitas, gera¸c˜ao de c´odigo, invers˜ao de onda, estˆencil

(6)

This project is inserted in the context of seismic imaging by inversion of acoustic waves, a problem of high computational cost which involves solving wave equations. Its central objective is the generation of a C code that is the algorithm for solving a partial differential equation, and that is based on the finite difference method.

In order for the problem to be formalized at a high level, the wave equation is repre-sented in a Domais-Specific Language that allows the equation to be written in a symbolic way, giving it simplicity and conciseness. Further, with this equation a stencil is created that uses the finite difference method to calculate the numeric values that satisfy it. Then, the high-level expression of the stencil is translated into a low-level expression, that is, the symbolic expression is transformed into an explicit indexing expression that allows accessing positions of a vector that represents the problem.

Thus, the achievements of this project were the creation of a parser that translates expressions from high to low level, and the generation of a C code that contains the solution algorithm for the partial differential equation that describes the problem. Such results can be used in seismic imaging projects, and the project itself can be continued and evolved in order to guarantee its operation with more complex equations and in order to support a wider range of problems.

Keywords – Domain-Specific Language, partial differential equation, finite difference method, code generation, wave inversion, stencil

(7)

1 Aquisi¸c˜ao de dados atrav´es de emiss˜ao de ondas e recep¸c˜ao das ondas

re-fletidas . . . 11

2 Esquema do fluxo de trabalho da invers˜ao da forma de onda completa . . . 13

3 Estˆencil de cinco pontos . . . 15

4 Estˆenceis de alta ordem . . . 15

5 Pilha funcional do Devito . . . 22

6 Cronograma do planejamento do projeto . . . 26

7 Representa¸c˜ao da condi¸c˜ao inicial da grade de u no primeiro passo de tempo 44 8 Representa¸c˜ao da condi¸c˜ao final da grade de u no ´ultimo passo de tempo . 45 9 Representa¸c˜ao da condi¸c˜ao final da grade de u gerada pelo Devito . . . 46

(8)

1 Introdu¸c˜ao 7 1.1 Objetivo . . . 7 1.2 Motiva¸c˜ao . . . 7 1.3 Justificativa . . . 9 1.4 Organiza¸c˜ao do Trabalho . . . 10 2 Aspectos Conceituais 11 2.1 Imageamento por Reflex˜ao S´ısmica . . . 11

2.2 Full-Waveform Inversion (FWI) . . . 12

2.3 Equa¸c˜oes Diferenciais Parciais e o M´etodo das Diferen¸cas Finitas . . . 13

2.4 Domain-Specific Language (DSL) . . . 16 3 Tecnologias Utilizadas 17 3.1 Linguagens de Programa¸c˜ao . . . 17 3.2 Bibliotecas . . . 18 3.2.1 Devito . . . 18 3.2.1.1 Prop´osito . . . 18 3.2.1.2 Aplica¸c˜ao . . . 19 3.2.2 Sympy . . . 22 4 Metodologia do Trabalho 25 4.1 Concep¸c˜ao . . . 25 4.2 Planejamento . . . 26 4.3 Execu¸c˜ao . . . 28 4.4 Fechamento . . . 28

5 Especifica¸c˜ao de Requisitos do Sistema 30 6 Projeto e Implementa¸c˜ao 32 6.1 Equa¸c˜ao de Onda e DSL do Devito . . . 32

6.2 Tradu¸c˜ao da DSL com Sympy . . . 33

6.3 Gera¸c˜ao de C´odigo: Template . . . 37

(9)

8 Considera¸c˜oes Finais 47 8.1 Conclus˜oes do Projeto de Formatura . . . 47 8.2 Contribui¸c˜oes . . . 49 8.3 Perspectivas de Continuidade . . . 49

(10)

1

INTRODUC

¸ ˜

AO

1.1

Objetivo

O presente trabalho est´a inserido no contexto do projeto STMI - Software Technolo-gies for Modeling and Inversion with Applications in Seismic Imaging, que ´e um projeto de pesquisa em execu¸c˜ao no RCGI - Research Centre for Gas Innovation, na Escola Po-lit´ecnica da USP. O contexto do projeto ´e investigar e criar tecnologias para simula¸c˜ao num´erica e solu¸c˜oes para o problema da invers˜ao s´ısmica. Essas tecnologias reduzir˜ao o tempo necess´ario para desenvolver e executar c´odigo para invers˜ao s´ısmica, um problema que, naturalmente, envolve a modelagem e simula¸c˜ao de problemas s´ısmicos que, por sua vez, dependem integralmente da resolu¸c˜ao de equa¸c˜oes diferenciais parciais (EDPs) que descrevem a propaga¸c˜ao das ondas ac´usticas em diferentes meios.

Dado esse contexto, o objetivo deste projeto ´e a gera¸c˜ao do c´odigo que resolve tais equa¸c˜oes de onda numericamente a partir de sua representa¸c˜ao em uma Domain-Specific Language (DSL). Assim, o projeto segue o seguinte caminho pr´e-estabelecido: as equa¸c˜oes de onda ser˜ao representadas em express˜oes de alto n´ıvel; tais express˜oes ser˜ao traduzidas para baixo n´ıvel atrav´es de algum tipo de compilador da DSL; a resolu¸c˜ao das equa¸c˜oes se dar´a pelo m´etodo das diferen¸cas finitas; e o c´odigo gerado que comp˜oe a solu¸c˜ao das equa¸c˜oes ser´a em linguagem C.

Para se atingir esse objetivo e seguir o plano de desenvolvimento, a implementa¸c˜ao de todas essas etapas ser´a efetuada com a linguagem de programa¸c˜ao Python, poderosa gra¸cas ao seu alto n´ıvel de abstra¸c˜ao e ao conjunto de pacotes cient´ıficos dispon´ıveis nessa linguagem, sendo que os mais importantes neste projeto foram o Devito e o SymPy.

1.2

Motiva¸

ao

O tema em foco neste projeto ´e a gera¸c˜ao do c´odigo que resolva EDPs particulares do problema de invers˜ao de onda, o que j´a vem sendo abordado e explorado por diferentes frentes.

Se por um lado temos ferramentas que nos permitem uma melhor e mais simples repre-senta¸c˜ao simb´olica de equa¸c˜oes matem´aticas, do outro temos aquelas que nos permitem uma gera¸c˜ao de c´odigo r´apida, eficiente, e as vezes at´e mesmo a gera¸c˜ao de um c´odigo j´a otimizado. E s˜ao esses dois elementos os focos principais do projeto, merecendo uma maior elabora¸c˜ao.

(11)

de qualquer outra linguagem dif´ıcil de ser representada diretamente em computadores, deve-se ressaltar a importˆancia de DSLs.

Domain-Specific Languages, por defini¸c˜ao, s˜ao a formaliza¸c˜ao de uma linguagem de programa¸c˜ao, que representam alguma aplica¸c˜ao espec´ıfica, como por exemplo equa¸c˜oes matem´aticas. Elas s˜ao, portanto, a ponte entre alguns problemas reais, e sua repre-senta¸c˜ao e solu¸c˜ao computacional.

Entretanto, como todas as demais linguagens, existem representa¸c˜oes simb´olicas mais simples e mais complexas, mais enxutas e mais extensas. As diferentes formas de se representar uma aplica¸c˜ao espec´ıfica s˜ao, portanto, um ponto de extrema importˆancia, e no caso espec´ıfico de equa¸c˜oes matem´aticas, ou mesmo de equa¸c˜oes de onda, tamb´em encontramos essa multiplicidade de op¸c˜oes e de caracter´ısticas. Aqui, as duas principais ferramentas examinadas e utilizadas em rela¸c˜ao `a representa¸c˜ao simb´olica s˜ao o SymPy e o Devito, ambas mais aprofundadas nas pr´oximas se¸c˜oes.

O segundo elemento fundamental do projeto ´e a gera¸c˜ao de c´odigo, o que n˜ao ´e um assunto novo no meio cient´ıfico.

A gera¸c˜ao de c´odigo pode ser observada em maior ou menor grau em ambientes de desenvolvimento integrado (em inglˆes, Integrated Development Environment - IDE), onde se gera c´odigo boilerplate ou se gera c´odigo com base em diagramas UML (Unified Mo-deling Language); em motores de templates, como por exemplo Jinja2, que permite gerar arquivos inteiros com uma l´ogica padr˜ao, mas com dados espec´ıficos; ou mesmo em algu-mas linguagens de programa¸c˜ao que permitem gera¸c˜ao de c´odigo em tempo de execu¸c˜ao atrav´es de fun¸c˜oes ou classes em modo template.

O presente caso, por´em, se afasta de todas essas formas de gera¸c˜ao de c´odigo, talvez se assemelhando um pouco mais apenas com motores de templates. Isso se d´a, pois de fato almeja-se uma l´ogica comum (o algoritmo que soluciona EDPs), e haja dados espec´ıficos (as diferentes equa¸c˜oes de onda e os dados de cada problema), mas no problema em foco existem dois pontos de divergˆencia.

Primeiro, quando soluciona-se EDPs numericamente, ´e comum se usar um estˆencil, que ser´a aprofundado mais adiante, mas que pode ser brevemente definido como um arranjo geom´etrico de pontos centrado no ponto que se deseja calcular. Este arranjo, por sua vez, representa aspectos do algoritmo usado para o c´alculo num´erico de cada ponto do problema. Tais estˆenceis, por´em, dependem de como se representa o problema e de como se decide calcular sua solu¸c˜ao, o que acarreta n˜ao s´o em uma mudan¸ca de dados caso a caso, mas efetivamente em uma mudan¸ca de l´ogica, fugindo dos motores de template.

O segundo ponto de divergˆencia ´e o processo de gera¸c˜ao em si, pois n˜ao se almeja inserir os dados da equa¸c˜ao em um template fixo, mas sim traduzir a representa¸c˜ao simb´olica da

(12)

equa¸c˜ao de onda para o c´odigo que a resolve. Esse segundo ponto tamb´em ´e trabalhado tanto pelo SymPy como pelo Devito, e portanto ser´a melhor elaborado posteriormente.

Evidencia-se, ent˜ao, que o foco do principal problema deste projeto e seus m´etodos de solu¸c˜ao, a saber, a representa¸c˜ao simb´olica e a gera¸c˜ao de c´odigo, est˜ao centrados nas duas ferramentas que mais foram estudadas e usadas ao longo de seu desenvolvimento. Assim, este trabalho se insere no contexto atual de solu¸c˜oes para os problemas descritos, al´em de contribuir diretamente para o corrente di´alogo no grande assunto dos problemas s´ısmicos.

1.3

Justificativa

Por tr´as deste projeto encontra-se est´ımulos tanto na comunidade cient´ıfica quanto na ind´ustria, pois as t´ecnicas de modelagem e simula¸c˜ao s´ısmica envolvem enorme custo computacional, enquanto o imageamento por reflex˜ao de onda envolve enorme custo mo-net´ario.

As causas do alto custo computacional est˜ao entrela¸cadas com conceitos t´ecnicos que ser˜ao mais aprofundados ao longo deste documento, como equa¸c˜oes diferenciais parciais, m´etodo das diferen¸cas finitas, e estˆencil.

O que pode ser dito agora, por´em, ´e que o c´odigo de resolu¸c˜ao das equa¸c˜oes de ondas ac´usticas cont´em ciclos aninhados, e, dependendo de como se representa o problema f´ısico em quest˜ao e de como se decide resolve-lo, pode-se aumentar consideravelmente tanto o n´umero de opera¸c˜oes quanto o n´umero de acessos `a mem´oria realizados. Al´em disso, o m´etodo de invers˜ao de onda em si envolve m´ultiplas itera¸c˜oes e trabalha com um enorme volume de dados, contribuindo ainda mais para a quest˜ao do custo computacional.

Fica evidente, ent˜ao, a necessidade de se otimizar o c´odigo gerado, mas isso n˜ao ´e algo que ser´a especificamente tratado neste projeto. Almeja-se apenas uma gera¸c˜ao consistente, eficiente, e simples, enquanto o aprimoramento da execu¸c˜ao e da utiliza¸c˜ao dos recursos computacionais ser˜ao deixados em aberto para projetos relacionados.

Contudo, deve-se adicionar que a simplicidade mencionada ´e crucial, dado que uma grande meta deste projeto ´e se tornar facilitador tanto das demais pesquisas e projetos subsequentes como, por exemplo, o aprimoramento do c´odigo gerado, quanto do di´alogo entre as diferentes partes envolvidas em quest˜oes de imageamento por reflex˜ao de onda, a saber, f´ısicos, matem´aticos, ge´ologos, e programadores.

J´a com rela¸c˜ao `as causas do alto custo monet´ario envolvido, estas s˜ao evidentes, pois a grande ´area de uso das t´ecnicas aqui envolvidas e desenvolvidas ´e da prospec¸c˜ao e extra¸c˜ao de petr´oleo offshore. Isso significa que a prioridade ´e iniciar perfura¸c˜oes em locais onde

(13)

se sabe, e n˜ao apenas se suspeita, que valha a pena. Caso contr´ario, a perfura¸c˜ao em solo oceˆanico, que j´a n˜ao ´e um processo simples e barato, enfrentaria perdas muito maiores e mais frequentes.

Finalmente, adiciona-se que a importˆancia deste projeto tamb´em se deve ao simples fato de as t´ecnicas e conceitos desenvolvidos estarem na base de problemas de enorme magnitude, evolvendo os grandes custos discutidos acima. Assim, sem uma base simples e bem feita, o resto se torna custoso e complexo em demasia.

1.4

Organiza¸

ao do Trabalho

O prop´osito deste documento, em sua totalidade, ´e cumprir com a elucida¸c˜ao do problema e da solu¸c˜ao do assunto tratado. Mais, ele almeja servir de referˆencia, ponto de partida, e fonte de inspira¸c˜ao, para projetos similares ou relacionados.

Com esses fins em mente, ´e necess´ario, em um primeiro momento, familiarizar os leitores com os conceitos, ferramentas, t´ecnicas, e ideias envolvidos no tema em quest˜ao, e s´o ent˜ao apresent´a-los `a implementa¸c˜ao e an´alise desenvolvidas subsequentemente.

Para tanto, come¸caremos com uma indispens´avel contextualiza¸c˜ao do projeto, abor-dando a ciˆencia que lhe d´a prop´osito e os desafios envolvidos que lhe d˜ao importˆancia. Tudo isso com o devido suporte bibliogr´afico.

A seguir, ser˜ao abordadas as tecnologias pertinentes ao entendimento e desenvolvi-mento do projeto, a metodologia que proporcionou seu planejadesenvolvi-mento e sua execu¸c˜ao, e os requisitos b´asicos para o correto funcionamento do mesmo.

Ap´os tratar de todos esses elementos de base e suporte, o pr´oximo assunto ser´a o pro-jeto em si. Ser˜ao tratadas tanto a implementa¸c˜ao do que foi desenvolvido para solucionar o problema, como a verifica¸c˜ao e valida¸c˜ao do comportamento esperado.

Finalmente, o trabalho ser´a encerrado com algumas ´ultimas considera¸c˜oes, versando sobre o que foi, ou deixou de ser, atingido, sobre as contribui¸c˜oes realizadas perante o meio acadˆemico-cient´ıfico, e sobre as alternativas existentes para incremento e continuidade do projeto.

(14)

2

ASPECTOS CONCEITUAIS

2.1

Imageamento por Reflex˜

ao S´ısmica

O elemento que contextualiza este projeto da forma mais abrangente ´e o imageamento por reflex˜ao s´ısmica, uma pr´atica que consiste na obten¸c˜ao de imagens topol´ogicas das camadas sub-superficiais terrestres atrav´es de medi¸c˜oes de reflexos de ondas [1].

Este processo consiste na emiss˜ao de ondas ac´usticas ou de press˜ao por uma ou mais fontes. A seguir, tais ondas viajam pelos diferentes meios em quest˜ao (´agua, g´as, sedi-mentos, rochas, etc) e s˜ao refletidas quando entram em contato com a fronteira entre dois materiais. Essa reflex˜ao ocorre devido ao contraste de propriedades entre os materiais [1] e, mais especificamente, devido `a impedˆancia ac´ustica, que ´e produto, e portanto de-pende, da velocidade de compress˜ao da onda e da densidade do material em quest˜ao [2]. Finalmente, as ondas refletidas s˜ao captadas por um ou mais receptores.

Um grande exemplo dessa t´ecnica s˜ao embarca¸c˜oes offshore de prospec¸c˜ao s´ısmica ao procurarem o lugar ideal para perfura¸c˜ao e explora¸c˜ao de dep´ositos de petr´oleo e g´as, como demonstrado na figura 1. Outros exemplos similares s˜ao de imageamento onshore ou no assoalho oceˆanico [3].

Figura 1: Aquisi¸c˜ao de dados atrav´es de emiss˜ao de ondas e recep¸c˜ao das ondas refletidas

Fonte: https://www.math.kit.edu/ianm3/seite/seismicimaging/en

Ao considerarmos os desafios t´ecnicos, operacionais, e ferramentais desse tipo de aplica¸c˜ao, sua importˆancia fica evidente ao considerarmos os alt´ıssimos custos envolvidos para perfura¸c˜oes, principalmente em solo oceˆanico, e o enorme desperd´ıcio de recursos

(15)

envolvido ao se come¸car uma explora¸c˜ao em solo pobre dos materiais procurados.

Assim, ´e inconteste a necessidade de m´etodos assertivos e precisos quando dessa ex-plora¸c˜ao, resultando em uma excelente aquisi¸c˜ao, an´alise, e transforma¸c˜ao dos dados obtidos.

2.2

Full-Waveform Inversion (FWI)

Para se realizar a t´ecnica de imageamento por reflex˜ao s´ısmica, ´e preciso haver al-gum m´etodo para analisar as ondas refletidas que foram captadas pelos receptores, e ´e precisamente esse o papel da invers˜ao da forma de onda completa, ou no inglˆes, full-waveform inversion. Mais especificamente, este ´e o m´etodo que permite criar imagens da sub-superf´ıcie terrestre com base nas ondas s´ısmicas refletidas, dado que elas contˆem informa¸c˜oes sobre as propriedades f´ısicas dos materiais ali encontrados [4].

Seu funcionamento baseia-se principalmente na descri¸c˜ao de um modelo que representa o problema f´ısico, o problema real, e cujo objetivo ´e predizer, atrav´es de simula¸c˜oes, as leituras dos receptores de onda dada a estrutura da sub-superf´ıcie terrestre [5]. Ou seja, com base em suposi¸c˜oes e estimativas premeditadas dos materiais que se espera encontrar na sub-superf´ıcie, ´e poss´ıvel realizar uma descri¸c˜ao matem´atica formal, o modelo, do campo de onda completa do problema em quest˜ao, para apenas ent˜ao se proceder `a invers˜ao [4].

A primeira parte da FWI consiste na resolu¸c˜ao das equa¸c˜oes de onda que se usou para modelar o problema. Esta etapa, tamb´em chamada de “problema direto”, envolve discretizar o modelo em um n´umero finito de pontos, ou seja, em uma grade de pontos (2D ou 3D), onde se deseja obter uma aproxima¸c˜ao num´erica da equa¸c˜ao de onda [5]. Tais equa¸c˜oes e sua discretiza¸c˜ao ser˜ao aprofundadas na pr´oxima sec¸c˜ao.

A segunda parte da invers˜ao, cujo nome ´e apropriadamente “problema inverso” se baseia n˜ao na obten¸c˜ao dos dados calculados atrav´es do modelo, mas na obten¸c˜ao dos dados reais captados pelos receptores. Nesta etapa, os valores captados s˜ao comparados aos calculados na primeira parte, e o erro entre ambos ´e registrado.

Finalmente, caso o erro seja inferior ao erro m´ınimo estipulado para o problema em quest˜ao, o processo de invers˜ao ´e finalizado. Caso contr´ario, o valor do erro ´e usado para se remodelar a equa¸c˜ao de onda na forma completa do modelo da itera¸c˜ao anterior [4], e ent˜ao o processo ´e repetido continuamente at´e que os ajustes alcancem um erro desprez´ıvel. O ciclo completo pode ser visto na figura 2.

(16)

Figura 2: Esquema do fluxo de trabalho da invers˜ao da forma de onda completa

Fonte: https://slim.gatech.edu/research/full-waveform-inversion

2.3

Equa¸

oes Diferenciais Parciais e o M´

etodo das

Diferen¸

cas Finitas

Descrita de forma generalizada, uma equa¸c˜ao diferencial parcial (EDP) ´e, natural-mente, uma equa¸c˜ao matem´atica que envolve derivadas parciais e que, em sua maioria, surgem de modelos f´ısicos [6].

O exemplo disso que ´e pertinente ao presente trabalho s˜ao as EDPs que representam a propaga¸c˜ao de uma onda, e mais especificamente, uma onda ac´ustica. Tais equa¸c˜oes descrevem o comportamento da onda no tempo e no espa¸co, podendo ser escrita em sua forma bi-dimensional pela equa¸c˜ao:

1 c2 ∗

∂2p ∂t2 − ∇

2p = 0 (2.1)

onde c representa a velocidade do som, p representa a fun¸c˜ao da press˜ao ac´ustica, depen-dente das vari´aveis espaciais x e y, e da vari´avel temporal t, e o termo ∇2 representa o Operador Laplaciano, que tamb´em pode ser escrito na forma:

∂2p ∂x2 +

∂2p

∂y2 (2.2)

Ainda, deve-se ressaltar que a fun¸c˜ao da press˜ao ac´ustica pode ser facilmente expan-dida para comportar as 3 dimens˜oes espaciais p(x, y, z).

A descri¸c˜ao de tais equa¸c˜oes de onda ´e essencial para o problema direto da FWI, mais especificamente a modelagem do problema. Descreve-las, por´em, ´e apenas metade da quest˜ao, sendo a outra metade referente `a simula¸c˜ao e, portanto, `a resolu¸c˜ao num´erica das EDPs.

O campo de m´etodos num´ericos oferece a solu¸c˜ao por meio de m´etodos de discretiza¸c˜ao, que nada mais significa do que obter a solu¸c˜ao num´ericas em pontos discretos do problema. Em outras palavras, opta-se por dividir o dom´ınio do problema em uma cole¸c˜ao de pontos espa¸cados que constituem uma grade [7], e calcular o valor da equa¸c˜ao somente em tais

(17)

pontos, em lugar de se calcular seu valor para todos os pontos que descrevem o problema em sua forma cont´ınua.

Dentre os m´etodos de discretiza¸c˜ao de ondas, o mais popular ´e o m´etodo das diferen¸cas finitas [4], ou no inglˆes finite difference method (FDM).

Esse m´etodo envolve, primeiramente, criar uma grade 2D ou 3D, cujos pontos est˜ao espa¸cados em intervalos regulares. Al´em disso, define-se tamb´em um intervalo regular no tempo, comumente chamado de passo de tempo. Esta etapa, como j´a dito, ´e a pr´opria discretiza¸c˜ao do dom´ınio do problema e deve-se garantir que a equa¸c˜ao seja cumprida para todos esses pontos discretos.

Em seguida, temos o passo mais essencial do m´etodo das diferen¸cas finitas, que ´e justamente substituir as derivadas por diferen¸cas finitas [7], o que pode ser feito de acordo com diferentes aproxima¸c˜oes.

Dentre as aproxima¸c˜oes cl´assicas podemos destacar a diferen¸ca progressiva e regressiva. A t´ıtulo de exemplo, caso a discretiza¸c˜ao ocorresse apenas no dom´ınio do tempo, isso significaria que a derivada do ponto que queremos calcular seria obtida a partir do passo seguinte no caso da diferen¸ca progressiva, e a partir do passo anterior no caso da diferen¸ca regressiva, ou seja, respectivamente:

u0(tn) ≈ un+1− un tn+1− tn , u0(tn) ≈ un− un−1 tn− tn−1 (2.3)

No caso de problemas mais complexos, como o presente, onde as derivadas s˜ao de segunda ordem no espa¸co, a aproxima¸c˜ao costuma ser obtida atrav´es de um estˆencil, que nada mais ´e que a expans˜ao do m´etodo descrito anteriormente nas outras dimens˜oes, ou seja, em lugar de usar o passo anterior ou posterior, se usa, tamb´em, os pontos espaciais vizinhos ao que se deseja calcular.

Um estˆencil extremamente caracter´ıstico ´e o estˆencil de cinco pontos, tamb´em chamado de quincˆoncio, ilustrado na figura 3. Este exemplo representa o c´alculo de um ponto, o n´o central, a partir de seus 4 vizinhos.

Ilustrando, ainda, a aplica¸c˜ao do estˆencil de forma matem´atica, pode-se usar o exemplo do estˆencil de cinco pontos no Operador Laplaciano, cujo resultado ´e:

∇2u(x, y) ≈ u(x − h, y) + u(x + h, y) + u(x, y − h) + u(x, y + h) − 4u(x, y)

h2 (2.4)

onde h representa o espa¸camento na grade espacial.

Deve-se acrescentar que existem outros estˆenceis de ordens maiores, ou seja, dependem de mais pontos vizinhos e de pontos vizinhos mais distantes do n´o central, o que ´e ilustrado

(18)

Figura 3: Estˆencil de cinco pontos

Fonte: https://www.researchgate.net/figure/Five-point-stencil fig2 228379661

na figura 4. Tais modelos de estˆencil, apesar de conferirem resultados mais precisos, s˜ao fonte de grande peso computacional, podendo elevar significativamente o n´umero de opera¸c˜oes envolvidas. Mais uma vez, a necessidade de otimiza¸c˜ao se mostra evidente.

Figura 4: Estˆenceis de alta ordem

Fonte: [8]

Finalmente, ap´os ter-se escolhido o m´etodo de discretiza¸c˜ao e substitu´ıdo as devidas derivadas, e dado que deseja-se calcular os valores da equa¸c˜ao de onda de forma compu-tacional e automatizada, resta apenas formular o algoritmo que executa todos os c´alculos necess´arios. Isso normalmente se d´a na forma de chamadas recursivas ou de loops ani-nhados que percorrem todo o escopo do problema, resolvendo a equa¸c˜ao numericamente

(19)

para cada ponto da grade espacial e em cada passo temporal.

2.4

Domain-Specific Language (DSL)

Uma linguagem de dom´ınio espec´ıfico, ou no inglˆes domain-specific language (DSL), ´e uma linguagem que ´e pensada, projetada, e propositalmente direcionada para uma aplica¸c˜ao de um dom´ınio espec´ıfico, junto de seus aspectos mais relevantes, como seus principais conceitos e caracter´ısticas [9].

Como tal, uma DSL ´e arquitetada para encapsular de forma concisa e focada as nota¸c˜oes e abstra¸c˜oes apropriadas pertencentes a tal aplica¸c˜ao, resultando em uma pode-rosa ferramenta de express˜ao [9].

Uma DSL, ent˜ao, quando feita com primor, permite trabalhar um problema espec´ıfico e complexo de forma simples, ou ao menos mais simples que sem o seu uso, ao mesmo tempo em que traz maior portabilidade, confiabilidade, otimizabilidade e testabilidade aos projetos que fazem seu uso [9].

Por fim, resta comentar que uma boa DSL adv´em do extenso conhecimento do dom´ınio da aplica¸c˜ao. ´E esse grande conhecimento que permite estruturar a DSL de modo que seu uso seja pr´atico e, como j´a dito, extremamente expressivo. E ´e exatamente isso que uma das principais ferramentas usadas nesse projeto faz, excluindo, assim, a necessidade de um exemplo nesta se¸c˜ao. Essa ferramenta ´e o Devito, e sua merecida descri¸c˜ao se encontra no pr´oximo cap´ıtulo.

(20)

3

TECNOLOGIAS UTILIZADAS

3.1

Linguagens de Programa¸

ao

A linguagem de programa¸c˜ao utilizada para o desenvolvimento e implementa¸c˜ao do projeto ´e a linguagem Python.

A primeira raz˜ao para essa escolha ´e dada pela grande adequa¸c˜ao dessa linguagem para altos n´ıveis de abstra¸c˜ao. Isso permite tanto representar problemas mais complexos de uma maneira mais clara e simples, como permite aproximar o c´odigo em si da linguagem humana.

O segundo motivo para esta escolha se d´a por conta do extenso ecossistema cient´ıfico proporcionado pelos m´odulos e bibliotecas dispon´ıveis nessa linguagem. Alguns deles ser˜ao tratados mais adiante dado que contribu´ıram plena e integralmente para a resolu¸c˜ao do problema em quest˜ao, mas a t´ıtulo de exemplo temos: SymPy, NumPy, Pandas, Matplo-tlib, e SciPy. S˜ao esses os pacotes que permitem fazer representa¸c˜oes simb´olicas, opera¸c˜oes matem´aticas complexas, tratamentos extensos de dados, desenhos de gr´aficos, entre mui-tos outros processos estimados pela comunidade cient´ıfica e que permitem resolu¸c˜oes efi-cientes de problemas.

Por ´ultimo, considera-se essencial que a presente implementa¸c˜ao possa ser interpre-tada, utilizada, modificada, e melhorada por todas as partes envolvidas no problema em quest˜ao. Ent˜ao, precisamente por conta dos dois motivos anteriores, temos que a lingua-gem Python, unida `a abstra¸c˜ao e aos pacotes que proporciona, ´e a mais apropriada para aproximar programadores, matem´aticos, ge´ologos, e f´ısicos. Com Python, a solu¸c˜ao se mostra eficaz, compreens´ıvel, eficiente, e extens´ıvel. ´E, portanto, a melhor op¸c˜ao.

O c´odigo gerado, por outro lado, sendo aquele que de fato aborda a resolu¸c˜ao das EDPs, ´e na linguagem C. O motivo principal para essa escolha tem origem no j´a mencionado alt´ıssimo custo computacional envolvido no problema da invers˜ao de onda. A linguagem C, por ser de baixo n´ıvel, e portanto mais pr´oxima do computador, nos permite aperfei¸coar a resolu¸c˜ao das EDPs no n´ıvel das opera¸c˜oes executadas e dos acessos `a mem´oria. Isso, por sua vez, confere `a solu¸c˜ao apenas uma parcela da carga que seria necess´aria caso se utiliza-se uma linguagem de alto n´ıvel ou caso n˜ao se fizesse otimiza¸c˜ao de execu¸c˜ao.

Em suma, a linguagem C ´e um dos principais elementos que permite a indispens´avel otimiza¸c˜ao computacional do problema.

(21)

3.2

Bibliotecas

Este projeto tem como principal base tecnol´ogica-computacional dois pacotes, ou bi-bliotecas, do Python: Devito e SymPy.

A primeira que ser´a descrita a seguir, o Devito, se configura como a principal fonte de inspira¸c˜ao e suporte computacional para este projeto, dado que ele foca, em parte, no mesmo problema de invers˜ao de onda na forma completa e em outras quest˜oes s´ısmicas que contextualizam este trabalho.

O intuito deste trabalho ´e justamente usar a DSL do Devito, mas implementar uma solu¸c˜ao diferente, ou ao menos paralela, `a que ele oferece em rela¸c˜ao `a resolu¸c˜ao de equa¸c˜oes de onda. Isso, como ser´a descrito adiante, foi feito atrav´es de uma engenharia reversa do Devito.

A segunda biblioteca que ser´a descrita, o SymPy, se configura como a principal via de resolu¸c˜ao deste projeto, dado que ´e justamente esse pacote que est´a por tr´as do Devito e lhe confere, assim como `a esse projeto, as abstra¸c˜oes e fun¸c˜oes necess´arias para manipular equa¸c˜oes matem´aticas, resolvˆe-las, e gerar c´odigo C.

3.2.1

Devito

3.2.1.1 Prop´osito

Devito ´e “uma DSL de diferen¸cas finitas que fornece computa¸c˜ao de estˆencil otimizada a partir de especifica¸c˜oes de problemas de alto n´ıvel com base em express˜oes simb´olicas de Python”[10]. Em outras palavras, o Devito ´e uma biblioteca do Python que fornece uma DSL espec´ıfica para se trabalhar com equa¸c˜oes de diferen¸cas finitas. Tal DSL per-mite representar as equa¸c˜oes de forma simb´olica, e portanto permite a representa¸c˜ao dos problemas f´ısicos e matem´aticos em alto n´ıvel. Al´em disso, dado que tais problemas ge-ralmente envolvem alto volume de dados e alto custo computacional, o Devito fornece uma resolu¸c˜ao por estˆencil fortemente otimizada. A t´ıtulo de exemplo, o c´odigo C gerado pelo Devito apresenta uso de paralelismo e diretivas pragma, mas ainda existem outros recursos de otimiza¸c˜ao [10].

Este projeto, por´em, foca apenas na DSL do Devito, e n˜ao em seu poder de otimiza¸c˜ao, dado que ´e justamente disso que se deseja desvencilhar. E a raz˜ao para isso ´e simples: usar a DSL para tratar de problemas matem´aticos complexos de uma forma computacional mais abstrata, ou seja, em alto n´ıvel, ao mesmo tempo em que se deixa em aberto a quest˜ao da otimiza¸c˜ao para especialistas em computa¸c˜ao de alto desempenho (no inglˆes, High-Performance Computing, HPC).

(22)

da FWI, colocando a representa¸c˜ao computacional do problema em um estado que possa ser compreendido e evolu´ıdo tanto por matem´aticos, f´ısicos, e ge´ologos quanto por de-senvolvedores de hardware e de software. Os primeiros se adequar˜ao facilmente `a DSL de alto n´ıvel e tratar˜ao da modelagem, enquanto os desenvolvedores se voltar˜ao para a busca de otimiza¸c˜oes computacionais, referentes `a simula¸c˜ao, conforme o sistema que for utilizado.

Mais especificamente, a importˆancia de se desvincular da otimiza¸c˜ao do Devito se d´a justamente na medida do controle que se ter´a sobre ela. A otimiza¸c˜ao pr´e-estabelecida e portanto “est´atica” (apesar de razoavelmente configur´avel e adapt´avel ao problema) do Devito, dar´a lugar a uma otimiza¸c˜ao “dinˆamica” criada por especialistas, que se adequar´a `

as especifica¸c˜oes do problema, do software, e do hardware utilizados.

3.2.1.2 Aplica¸c˜ao

O Devito ´e uma biblioteca bastante extensa, e ele ataca problemas matem´aticos varia-dos atrav´es de suas in´umeras funcionalidades. Portanto, para evitar uma reprodu¸c˜ao pro-longada e desnecess´aria do que pode ser encontrado em sua vasta documenta¸c˜ao, optou-se por registrar aqui somente o necess´ario para o entendimento do comportamento do Devito exclusivamente relacionado ao projeto, e n˜ao de sua estrutura geral, muito menos de seus detalhes de implementa¸c˜ao ou modo de opera¸c˜ao.

A pe¸ca central do Devito que foi usada neste projeto e que merece maior elabora¸c˜ao ´e o poder de sua DSL. ´E ela que permite representar uma equa¸c˜ao diferencial de modo incrivelmente conciso, l´ogico e simples.

Essas caracter´ısticas s˜ao poss´ıveis gra¸cas ao SymPy, que comp˜oe a base do Devito, permitindo-o tratar equa¸c˜oes de forma simb´olica. O que os desenvolvedores do Devito fizeram foi apenas criar abstra¸c˜oes mais espec´ıficas e poderosas para se trabalhar com equa¸c˜oes diferenciais mais facilmente.

Para ilustrar essa facilidade, elabora-se a seguir como criar uma fun¸c˜ao e alguns exem-plos de como manipula-la.

Primeiro, define-se uma grade que diz em quais dimens˜oes espaciais o problema est´a definido, e em quantos intervalos cada dimens˜ao se divide. E em seguida, define-se a fun¸c˜ao atrelada `a essa grade e, tamb´em, se ela ´e relativa ao tempo ou n˜ao:

# Grade que d i v i d e 1 metro no e i x o x e no e i x o y em 20 e s p a ¸c o s g r i d = Grid ( s h a p e =(20 , 2 0 ) , e x t e n d = ( 1 . , 1 . ) )

# Fun¸c ˜ao de nome u , no dom´ı n i o x e y ( r e f e r e n t e `a g r a d e ) , e no tempo u = TimeFunction ( name=‘u ’ , g r i d=g r i d )

(23)

A vari´avel ‘u’ representa, ent˜ao, a fun¸c˜ao u(t, x, y) e algumas de suas manipula¸c˜oes mais comuns s˜ao:

• u.dt : Representa a derivada parcial de u em t ∂

∂tu(t, x, y) (3.1)

• u.dxl : Representa a derivada parcial de u em x ∂

∂xu(t, x, y) (3.2)

sendo que sua discretiza¸c˜ao se d´a com o estˆencil que usa o ponto atual e o ponto anterior u(x, y) hx −u(x − hx, y) hx (3.3)

• u.dxr : Representa a derivada parcial de u em x ∂

∂xu(t, x, y) (3.4)

sendo que sua discretiza¸c˜ao se d´a com o estˆencil que usa o ponto atual e o ponto posterior u(x + hx, y) hx −u(x, y) hx (3.5)

• u.dy2 : Representa a derivada parcial em segundo grau de u em y

∂2

∂y2u(t, x, y) (3.6)

• u.forward : Representa a fun¸c˜ao com um passo dt no tempo

u(t + dt, x, y) (3.7)

• u.dt.evaluate : Representa o estˆencil que discretiza a derivada parcial de u em t

−u(t, x, y)

dt +

u(t + dt, x, y)

dt (3.8)

Esses exemplos deixam evidente o car´ater sint´etico da DSL e ´e a combina¸c˜ao dessas manipula¸c˜oes que permite a constru¸c˜ao de uma equa¸c˜ao de modo quase literal:

eq = Eq ( u . dt2 − u . l a p l a c e ) Tal equa¸c˜ao representa:

− ∂ 2 ∂x2u(t, x, y) − ∂2 ∂y2u(t, x, y) + ∂2 ∂t2u(t, x, y) = 0 (3.9)

(24)

Agora, o que tamb´em ´e incrivelmente valioso ´e uma fun¸c˜ao do Devito chamada “solve”. Esta fun¸c˜ao ´e profundamente ligada ao SymPy, j´a que este possui uma fun¸c˜ao de mesmo nome e realiza basicamente a mesma atividade. A diferen¸ca ´e que o Devito adaptou a fun¸c˜ao do SymPy para trabalhar com sua pr´opria DSL.

´

E com esta fun¸c˜ao que ´e poss´ıvel criar um estˆencil j´a rearranjado para um desejado parˆametro, ou seja, isola-se do lado esquerdo da equa¸c˜ao o termo que se deseja obter, e do lado direito todo o resto da equa¸c˜ao que ser´a usado para obtˆe-lo.

Rearranjando a equa¸c˜ao anterior para o passo seguinte no tempo, pode-se simples-mente escrever:

s o l v e ( eq , u . f o r w a r d )

Essa fun¸c˜ao incrivelmente concisa retorna:

u(t + dt, x, y) = dt2(−2.0u(t, x, y) h2 y +u(t, x, y − hy) h2 y +u(t, x, y + hy) h2 y −2.0u(t, x, y) h2 x + u(t, x − hx, y) h2 x +u(t, x + hx, y) h2 x + 2.0u(t, x, y) dt2 − u(t − dt, x, y) dt2 ) (3.10)

Finalmente, a ´ultima parte fundamental a ser mencionada ´e o objeto do Devito cha-mado “Operator”. ´E com este objeto que ´e poss´ıvel transformar a express˜ao simb´olica do estˆencil em indexamento expl´ıcito, ou seja, transformar os s´ımbolos da equa¸c˜ao em acessos `a vetores, passando de, por exemplo, u(t, x, y), para u[t][x][y]. Ainda, ´e com a manipula¸c˜ao deste objeto que se gera o c´odigo C j´a otimizado que resolve a equa¸c˜ao.

O objetivo deste projeto, por´em, ´e justamente obter apenas parte da funcionalidade deste objeto. Almeja-se gerar o c´odigo que resolve a equa¸c˜ao, ao mesmo tempo em que se deixa de lado a otimiza¸c˜ao, portanto maiores detalhes de suas funcionalidades n˜ao convˆem.

Em termos pr´aticos, aquilo do Devito que se utiliza s˜ao a sua DSL e a fun¸c˜ao “solve”, ambos amplamente embasados no SymPy, enquanto que aquilo que se deseja reproduzir, tamb´em atrav´es do SymPy, ´e a tradu¸c˜ao da express˜ao simb´olica em indexamento expl´ıcito, e a gera¸c˜ao de c´odigo. Este ´ultimo, por sua vez, ser´a obtido a partir de uma engenharia reversa do c´odigo gerado pelo “Operator”.

Para resumir, a figura 5 representa os cinco n´ıveis fundamentais do Devito, dentre os quais s˜ao usados os dois primeiros, almeja-se reproduzir parcialmente os pr´oximos dois, e ser´a deixado de lado o ´ultimo.

(25)

Figura 5: Pilha funcional do Devito

Fonte: [10]

3.2.2

Sympy

A principal ferramenta que est´a por tr´as do Devito e deste projeto ´e o SymPy, e a raz˜ao para isso, como o pr´oprio nome desta biblioteca sugere, ´e que o SymPy lida com a computa¸c˜ao simb´olica de objetos matem´aticos na linguagem de programa¸c˜ao Python. Isso significa que os objetos matem´aticos s˜ao representados exatamente como intencionado e n˜ao atrav´es de uma aproxima¸c˜ao computacional. Um exemplo que ilustra bem essa situa¸c˜ao, e o mesmo oferecido no in´ıcio da documenta¸c˜ao do SymPy, ´e o caso de ra´ızes quadradas. Quando uma raiz n˜ao ´e exata, ela ser´a avaliada para uma aproxima¸c˜ao do seu valor: a raiz de 3, por exemplo, ´e avaliada para 1.7320508075688772 no terminal do Python. O que o SymPy faz ´e permitir que a raiz de 3 seja representada pelo seu s´ımbolo, ou seja, sqrt(3) no Python, que equivale a √3. Al´em disso, e talvez mais interessante, o SymPy permite que vari´aveis n˜ao inicializadas sejam mantidas em sua forma simb´olica, ou seja, se escrevermos algo como a + b + c o SymPy representar´a essa express˜ao exatamente como ela est´a, enquanto o Python retornaria um erro, j´a que n˜ao temos os valores de a, b ou c.

Novamente, n˜ao compete a este documento reproduzir o que j´a pode ser encontrado minuciosamente descrito e exemplificado na documenta¸c˜ao desta biblioteca. Por´em, aquilo que foi indispens´avel para a execu¸c˜ao do projeto merece algumas considera¸c˜oes `a respeito de seu funcionamento. Essas funcionalidades essenciais est˜ao divididas em 3 grandes m´odulos do SymPy: “core”, “codegen”, e “printing”.

(26)

O m´odulo “core” ´e, obviamente, o n´ucleo do SymPy. ´E com ele que se torna poss´ıvel trabalhar com express˜oes simb´olicas, sendo que seus elementos mais utilizados ao longo do projeto foram justamente “Symbol” e “Eq”.

“Symbol” ´e o que permite definir uma vari´avel n˜ao inicializada como um s´ımbolo, de modo que seja poss´ıvel usa-lo em sua forma simb´olica em uma express˜ao, e n˜ao em sua forma avaliada. ´E poss´ıvel criar um s´ımbolo da seguinte forma:

a = Symbol ( ‘ a ’ )

J´a “Eq”, abrevia¸c˜ao de “Equality”, representa uma igualdade que possibilita repre-sentar algo como c2 = a2+ b2 (dado que os s´ımbolos a, b, e c j´a foram criados) da seguinte forma:

eq = Eq ( c ∗ ∗ 2 , a ∗∗2 + b ∗ ∗ 2 )

O segundo m´odulo mais utilizado, “codegen”, ´e o m´odulo que, naturalmente, possibi-lita trabalhar com a gera¸c˜ao de c´odigo em in´umeras linguagens de programa¸c˜ao.

Aquilo que ele oferece que ´e de maior interesse para o projeto ´e sua abordagem para com a ´arvore sint´atica abstrata, ou no inglˆes, Abstract Syntax Tree (AST), atrav´es da qual o SymPy reconhece e organiza os elementos do c´odigo a ser gerado.

A AST ´e uma estrutura de dados em forma de ´arvore que representa a sintaxe de um c´odigo escrito com uma linguagem de programa¸c˜ao. Atrav´es dela ´e poss´ıvel distinguir e analisar os diferentes elementos sint´aticos que comp˜oe o c´odigo, tal como declara¸c˜oes, tipos de elementos, strings, vetores, ciclos “for”, ciclos “while”, chamadas de fun¸c˜oes, etc. Para ilustrar de alguma forma estes conceitos, ser˜ao descritos mais a fundo aqueles elementos sint´aticos do SymPy mais utilizados na implementa¸c˜ao do projeto.

• Assignment: representa a atribui¸c˜ao de um valor para alguma vari´avel. Por exemplo, o c´odigo

x = x + 1 ;

pode ser representado por

a s s i g n m e n t = Assignment ( x , x + 1 )

• Declaration: representa a declara¸c˜ao de uma vari´avel. Por exemplo, o c´odigo i n t x ;

pode ser representado por

d e c l a r a t i o n = D e c l a r a t i o n ( ’ x ’ )

(27)

• Element: representa um elemento de um vetor. Por exemplo, o peda¸co de c´odigo para acesso de um vetor por indexamento

v [ i ] [ j ] [ k ]

pode ser representado por

e l e m e n t = Element ( ‘ v ’ , ‘ i j k ’ )

• For: representa um ciclo “for”, contendo sua inicializa¸c˜ao, condi¸c˜oes, e corpo. Por exemplo, o c´odigo

f o r ( i = 0 , i < 1 0 , i +=1) { x = x + 1 ;

}

pode ser representado por

f o r i = For ( i , Range ( 1 0 ) , [ Assignment ( x , x + 1 ) ] )

• FunctionPrototype: representa a assinatura de uma fun¸c˜ao, contendo seu nome, o tipo de seu retorno, e seus parˆametros. Por exemplo, o c´odigo

double f u n c t i o n ( double a , double b )

pode ser representado por

p r o t o t y p e = F u n c t i o n P r o t o t y p e ( r e a l , ’ f u n c t i o n ’ , [ a , b ] )

Finalmente, o terceiro e ´ultimo m´odulo de suma importˆancia, “printing”, ´e aquele que traduz as express˜oes simb´olicas descritas com o SymPy, seja usando o m´odulo “core”, seja usando “codegen”, ou at´e uma combina¸c˜ao de ambos, na express˜ao correspondente `

a linguagem de programa¸c˜ao desejada. O SymPy possibilita traduzir as express˜oes em in´umeras linguagens, como Java, Fortran, Latex, Rust, entre muitas outras, dentre as quais aquela que foi usada no projeto ´e a linguagem C.

Para se obter a express˜ao correspondente na linguagem C, utiliza-se o m´etodo “ccode”. E seu uso j´a foi demonstrado nos exemplos dos elementos da AST acima, dado que se as chamadas “ccode(assignment)”, “ccode(declaration)”, “ccode(for i)”, ou “ccode(elem)” forem feitas, elas retornar˜ao precisamente o c´odigo que foi dado em cada exemplo.

Ainda, ´e importante ressaltar que outras funcionalidades do SymPy foram usadas e experimentadas ao longo do projeto, mas o que foi aqui apresentado representa fielmente o centro de interesse e de aplica¸c˜ao para a solu¸c˜ao do problema proposto.

(28)

4

METODOLOGIA DO TRABALHO

4.1

Concep¸

ao

Reiterando e resumindo o que foi elaborado nas se¸c˜oes anteriores, a necessidade deste projeto prov´em, mais genericamente, da necessidade de se trabalhar computacional e programaticamente com problemas matem´aticos e f´ısicos que podem envolver alto custo computacional e, por vezes, alto custo monet´ario. Mais especificamente, ´e necess´ario viabilizar os meios de se resolver equa¸c˜oes diferenciais parciais para que isso possa ser usado em ferramentas de invers˜ao de onda na forma completa. Al´em disso, isso deve ser feito de uma maneira que seja compreens´ıvel para as diferentes partes que integram problemas s´ısmicos.

Portanto, define-se a quest˜ao e meta centrais deste projeto como sendo a imple-menta¸c˜ao de uma ferramenta que resolva equa¸c˜oes diferenciais parciais, ao mesmo tempo em que se preza pela simplicidade, compreensibilidade, e facilidade tanto de uso como de evolu¸c˜ao. J´a a viabilidade de se alcan¸car essa meta se d´a na medida em que este projeto se inspira e se baseia em outras solu¸c˜oes para problemas similares, e devido `as excelentes ferramentas existentes que servem de suporte ao presente trabalho.

Al´em disso, essas solu¸c˜oes e ferramentas, principalmente o Devito e o SymPy, s˜ao os recursos fundamentais que garantem que as caracter´ısticas almejadas (simplicidade, compreensibilidade, etc) sejam acatadas. Por´em, ainda ´e necess´ario ressaltar que sem as facilidades da linguagem Python e seu grande ecossistema cient´ıfico, isso se tornaria bem mais dif´ıcil. Ainda, devido ao contexto do projeto destacar o alto custo computacional dos problemas envolvidos, faz-se tamb´em necess´ario a velocidade da solu¸c˜ao em resolver as equa¸c˜oes, e a possibilidade de otimizar tal solu¸c˜ao para problemas ou elementos de hardware espec´ıficos. Aqui, ent˜ao, ´e que se faz necess´ario a presen¸ca de uma linguagem de baixo n´ıvel, como a linguagem C, para atacar essas exigˆencias.

Define-se, ent˜ao, a proposta do projeto como sendo implementar um programa em linguagem Python que gere um c´odigo C, esse sim, que resolva as equa¸c˜oes diferenciais parciais. Mais, isso ser´a feito com a engenharia reversa do Devito, e com total suporte do SymPy. Assim, todas as metas se tornam fact´ıveis e o projeto pode ser implementado com a garantia de alcan¸car um estado funcional e v´alido.

(29)

4.2

Planejamento

O planejamento do projeto consiste de trˆes partes distintas, como pode ser visto na fi-gura 6. Suas subdivis˜oes representam os pontos mais importantes de todo o percurso deste projeto, e o intervalo de tempo que lhes foi destinado foi seguido sem muitas distor¸c˜oes.

Figura 6: Cronograma do planejamento do projeto

A primeira, “Atividades Prim´arias”, diz respeito ao di´alogo inicial entre as partes envolvidas, o aluno e os orientadores. Foi nessa etapa onde se delimitou o escopo do projeto, se definiu suas metas, e se elucidou seu motivo de vir a ser.

O essencial a destacar nessa etapa s˜ao os estudos preliminares e a familiariza¸c˜ao com as ferramentas. Ambos foram cardinais para o correto entendimento do que se desejava e de como isso seria alcan¸cado. Os estudos se voltaram mais para como se trabalhar com a resolu¸c˜ao de equa¸c˜oes atrav´es do Python, enquanto as ferramentas que necessitavam de familiariza¸c˜ao foram, sem surpresa, o Devito e o SymPy.

Essa familiariza¸c˜ao foi necess´aria pois ambas as bibliotecas s˜ao extensas e porque seu funcionamento e como utiliza-las de modo vantajoso em dado contexto n˜ao s˜ao necessa-riamente aparentes de imediato. Al´em disso, havia bastante material de referˆencia, como a documenta¸c˜ao do c´odigo, v´ıdeos de palestras dos respons´aveis por cada ferramenta, e artigos cient´ıficos, dentre os quais os mais ´uteis s˜ao mencionados na bibliografia.

A segunda parte, “Atividades do Projeto”, envolve as etapas mais ´obvias de um tra-balho de conclus˜ao de curso direcionado `a engenharia de computa¸c˜ao, com a aloca¸c˜ao de um tempo aproximadamente igual entre revis˜ao bibliogr´afica, implementa¸c˜ao do c´odigo, e reda¸c˜ao da monografia. Ainda, foi alocado um tempo extra dedicado `a valida¸c˜ao do que foi desenvolvido.

(30)

Essa divis˜ao, contudo, ´e um tanto quanto simplificada no que diz respeito `a imple-menta¸c˜ao e, portanto, cabe aqui uma enumera¸c˜ao de suas principais submetas.

Os grandes passos representativos de real progresso no trabalho s˜ao:

1. Representar uma equa¸c˜ao de onda usando o Devito. A complexidade do problema pode variar desde uma simples equa¸c˜ao de onda, at´e um elaborado modelo s´ısmico. A representa¸c˜ao ao final do projeto seria escolhida de acordo com o tempo dispon´ıvel para sua correta implementa¸c˜ao.

2. Traduzir a representa¸c˜ao da equa¸c˜ao de onda usando o SymPy, de modo que ao inv´es de se ter uma representa¸c˜ao simb´olica, tenha-se uma estrutura de dados. Em outras palavras, traduzir a express˜ao em alto n´ıvel (ex.: u(t, x, y)), em uma express˜ao de baixo n´ıvel com indexamento expl´ıcito (ex.: u[t][x][y]).

3. Gerar um arquivo C correspondente `a resolu¸c˜ao da equa¸c˜ao de onda com um m´ınimo de c´odigo gerado e um m´aximo de c´odigo j´a em um template definido. Esse passo de transi¸c˜ao ´e necess´ario para verificar se a tradu¸c˜ao da etapa anterior ´e funcional e compil´avel, sendo justamente essa tradu¸c˜ao o c´odigo gerado.

4. Gerar um arquivo C correspondente `a resolu¸c˜ao da equa¸c˜ao de onda com um m´aximo de c´odigo gerado e um m´ınimo de c´odigo j´a em um template definido. Essa ´e a forma ´ultima do que se deseja alcan¸car, onde quase todo o c´odigo ´e gerado atrav´es do SymPy especificamente para cada caso, e o template n˜ao passa de um pequeno header ou o m´ınimo necess´ario.

Os detalhes da implementa¸c˜ao de cada um desses passos, junto de se foi poss´ıvel total ou apenas parcialmente alcan¸c´a-los ser´a descrito na se¸c˜ao apropriada.

Finalmente, resta salientar que o maior ou menor grau de complexidade que se conse-guiu alcan¸car em cada passo tem rela¸c˜ao direta com o tempo dispon´ıvel para a realiza¸c˜ao do projeto. Esse maior ou menor grau, contudo, n˜ao representa real inconveniˆencia para o prop´osito do projeto, dado que ele ser´a integrado `a um projeto maior que poder´a lhe dar continuidade gra¸cas ao presente documento e `a aten¸c˜ao `a extensibilidade que foi dada na implementa¸c˜ao do c´odigo.

A ´ultima parte, “Atividades Acadˆemicas”, faz referˆencia apenas ao acompanhamento e avalia¸c˜ao do projeto por parte da universidade. Esta parte n˜ao necessita maior elabora¸c˜ao.

(31)

4.3

Execu¸

ao

Esta subse¸c˜ao se volta n˜ao para o que foi executado, mas sim para a abordagem com que se resolveu executar as tarefas descritas no planejamento, primeiro tratando de todas as tarefas anteriores `a implementa¸c˜ao e, depois, da implementa¸c˜ao em si.

Com rela¸c˜ao `as atividades preliminares j´a foi mencionado o material utilizado, mas em se tratando do m´etodo utilizado, aquele que foi mais r´apido para a compreens˜ao das ferramentas foi seguir e fazer pequenos experimentos com seus tutoriais dispon´ıveis em formato Jupyter Notebook, uma aplica¸c˜ao web que suporta documenta¸c˜ao com “live code”, ou seja, c´odigo que pode ser executado e experimentado ao longo do documento. Isso, somado com os v´ıdeos de palestra achados online, foram essenciais para dar in´ıcio `a estrutura¸c˜ao de como as ferramentas seriam utilizadas na fase de implementa¸c˜ao.

A segunda atividade que antecedeu a implementa¸c˜ao foi a pesquisa bibliogr´afica, e ela foi extremamente valiosa para situar o problema nos diferentes n´ıveis de contextualiza¸c˜ao que ele necessita. Sem compreender os conceitos de imageamento por reflex˜ao s´ısmica, FWI, equa¸c˜oes diferenciais parciais, e DSLs, seria mais dif´ıcil realizar um projeto com esse grau de complexidade e no curto intervalo de tempo dispon´ıvel para fazˆe-lo, pois n˜ao seria poss´ıvel distinguir categoricamente o que deve ser priorizado do que n˜ao deve. Em outras palavras, essa foi a abordagem utilizada para se executar o projeto; foi priorizado o absolutamente necess´ario para se atingir resultados v´alidos e uma ferramenta que pode facilmente integrar o grande projeto em que este est´a inserido.

Finalmente, com rela¸c˜ao `a implementa¸c˜ao em si, e dado o foco em prioriza¸c˜ao menci-onado, o protocolo sempre foi atingir um dos passos mencionados no planejamento antes de mudar para o pr´oximo. Al´em disso, cada passo foi atingido primeiro com o caso mais simples, para somente ent˜ao, e apenas com disponibilidade de tempo, partir para um caso mais complexo ou uma forma mais gen´erica de implementa¸c˜ao, expandindo o alcance da aplica¸c˜ao.

Ao fim, foi poss´ıvel garantir uma implementa¸c˜ao de cada passo mais, ou menos, com-plexo e/ou gen´erico, como ser´a discutido mais adiante.

4.4

Fechamento

Por ´ultimo, deve-se falar da abordagem escolhida em rela¸c˜ao ao fechamento do projeto, ou seja, em rela¸c˜ao `a valida¸c˜ao, `a avalia¸c˜ao, e `a evolu¸c˜ao deste trabalho.

J´a que este projeto foi concebido, planejado, e executado, tendo por base a engenharia reversa do Devito, n˜ao h´a nada mais l´ogico do que valid´a-lo com compara¸c˜oes diretas aos resultados obtidos no Devito. ´E necess´ario lembrar, por´em, que este projeto almeja

(32)

alcan¸car a mesma, ou similar, funcionalidade que o Devito, e n˜ao sua performance, j´a que isso ficar´a a cargo de especialistas em otimiza¸c˜ao. Portanto o que se espera s˜ao resultados compat´ıveis, e n˜ao um c´odigo C mais avan¸cado e mais r´apido.

A avalia¸c˜ao do que foi ou n˜ao foi alcan¸cado, ou se foi parcial ou totalmente alcan¸cado, ficar´a a cargo das considera¸c˜oes finais deste documento. Por´em, como j´a mencionado, qualquer falta que n˜ao compromete o funcionamento do c´odigo n˜ao prejudica a proposta ulterior deste trabalho, que ´e ser integrado em outro projeto, dado que ele poder´a ser facilmente continuado por vias deste documento e da apresenta¸c˜ao do c´odigo em si. Assim, a evolu¸c˜ao das ideias e utilidades aqui desenvolvidos poder´a ser executada.

Finalmente, resta real¸car que este documento ´e pe¸ca essencial do fechamento do pro-jeto, dado que ele re´une, na forma mais did´atica poss´ıvel, os conhecimentos sobre todos os n´ıveis de contextualiza¸c˜ao, sobre todo o ferramental utilizado, e sobre a solu¸c˜ao imple-mentada do problema multidisciplinar que foi tema deste projeto.

(33)

5

ESPECIFICAC

¸ ˜

AO DE REQUISITOS DO

SISTEMA

Este projeto foi desenvolvido com a linguagem de programa¸c˜ao Python e ele se destina a integrar outros projetos em Python que tratam de imageamento s´ısmico. Com isso em mente, ´e desejado que o presente projeto possa ser usado e evolu´ıdo sem impedimentos por conta de qualquer dependˆencia ou requisito de sistema, todos detalhados a seguir.

Como dito, o programa foi implementado em Python, mais especificamente a vers˜ao 3.8.3 e, portanto, para execut´a-lo ´e necess´ario possuir algum interpretador do Python atual o suficiente. Assim, recomenda-se usar as ´ultimas vers˜oes dispon´ıveis do Python 3.6, 3.7, ou 3.8. N˜ao ´e garantido que vers˜oes mais antigas funcionem corretamente, e de modo algum se recomenda Python 2, recentemente descontinuado.

Com rela¸c˜ao `as dependˆencias, o programa faz uso de quatro bibliotecas que devem ser instaladas antes de se executar o programa. Todas essas dependˆencias est˜ao em um arquivo no programa chamado requirements.txt, e recomenda-se que sua instala¸c˜ao seja feita atrav´es do gerenciamento de pacotes do Python, pip, o que pode ser feito com o comando: pip install -r requirements.txt. Existem, por´em, comandos similares em outros gerenciadores de pacotes como Anaconda.

Ainda com rela¸c˜ao `as dependˆencias, cabe aqui uma breve descri¸c˜ao de cada uma:

• Devito: j´a descrito anteriormente e indispens´avel para a realiza¸c˜ao do projeto, a instala¸c˜ao do Devito segue as recomenda¸c˜oes de sua pr´opria documenta¸c˜ao. E´ recomendado instalar o Devito pelo pip, chamando seu reposit´orio Git, ou seja, “git+https://github.com/devitocodes/devito.git” (j´a presente no arquivo de reque-rimentos);

• SymPy: j´a descrito anteriormente e tamb´em essencial para a implementa¸c˜ao do projeto;

• NumPy: biblioteca de opera¸c˜oes matem´aticas, vetoriais, e matriciais incrivelmente poderosa. Usada rapidamente apenas para passar, eficientemente, alguns dados do problema para o template que gera o c´odigo C;

• Jinja2: essa biblioteca ´e um motor de templates, ou seja, permite passar valores do c´odigo Python para um template pr´e-estabelecido em qualquer linguagem de programa¸c˜ao, no caso, C. Essa ferramenta trata da descri¸c˜ao de um template que cont´em elementos est´aticos, como um header e uma fun¸c˜ao main, enquanto que os demais elementos do problema, os elementos dinˆamicos que mudam caso a caso,

(34)

s˜ao exportados direto do programa em Python, como o algoritmo de resolu¸c˜ao de ondas, seus parˆametros, e os dados do problema.

Novamente, como o intuito deste projeto ´e ser usado e continuado em projetos de maior escala, a simplicidade de seus requisitos de funcionamento ´e intencional. Assim, apenas um interpretador recente e uma instala¸c˜ao feita atrav´es de um ´unico comando j´a s˜ao suficientes para executar o programa. E com rela¸c˜ao ao baixo volume de dependˆencias, os problemas aqui tratados j´a foram e ainda s˜ao abordados por poderosas ferramentas do enorme ecossistema cient´ıfico na linguagem Python. Assim, fez-se uso apenas do indispens´avel.

Finalmente, com rela¸c˜ao aos requisitos do c´odigo C gerado, ´e necess´ario apenas um compilador. Recomenda-se o conhecido gcc (GNU Compiler Collection). Al´em disso, o c´odigo gerado deve ser compilado com a flag −lm, que procura e liga a biblioteca libm, dado que no header do c´odigo C gerado ´e feita uma referˆencia `a biblioteca “math.h”. Fora isso, o c´odigo foi feito para funcionar corretamente por si s´o.

(35)

6

PROJETO E IMPLEMENTAC

¸ ˜

AO

Esta se¸c˜ao ´e dedicada a uma elabora¸c˜ao detalhada da forma como foram implemen-tados os grandes passos definidos no planejamento.

Almeja-se descrever como o t´opico principal de cada passo foi atingido, de forma que todos eles possam ser n˜ao apenas compreendidos, mas tamb´em que eles possam ser facilmente continuados, aumentando-se a complexidade da ferramenta e a abrangˆencia de sua aplica¸c˜ao em problemas ligados ao imageamento s´ısmico.

6.1

Equa¸

ao de Onda e DSL do Devito

Como antecipado no planejamento, a complexidade do problema trabalhado depen-deria do tempo dispon´ıvel para sua conclus˜ao e do progresso de seu desenvolvimento ao longo do tempo alocado.

O cen´ario que certamente mais beneficiaria o grande projeto que engloba este, seria o caso onde o problema s´ısmico j´a poderia ser descrito por completo, isto ´e, onde se pudesse formalizar um modelo matem´atico que inclu´ısse as fontes das ondas sonoras, os receptores, uma geometria mais elaborada, e condi¸c˜oes de borda bem definidas. Contudo, chegou-se a conclus˜ao que isso seria complexo demais para se desenvolver no curto prazo dispon´ıvel. Optou-se, portanto, por ater-se ao tema que intitula este documento e trabalhar apenas com equa¸c˜oes de onda, e n˜ao modelos completos.

Assim, adotou-se a equa¸c˜ao de onda em sua forma bi-dimensional mais gen´erica:

1 c2 ∗

∂2p ∂t2 − ∇

2p = 0 (6.1)

Com a equa¸c˜ao de onda estabelecida, o pr´oximo passo seria traduzi-la para a DSL do Devito, o que, como demostrado anteriormente, n˜ao traz grandes dificuldades dado o grande poder sint´etico do Devito.

Para formar a equa¸c˜ao de onda basta definir uma grade e uma fun¸c˜ao temporal, ambas levando em conta as dimens˜oes x e y. A t´ıtulo de exemplo temos:

g r i d = Grid ( s h a p e =(21 , 2 1 ) , e x t e n t = ( 1 . , 1 . ) )

u = TimeFunction ( name= ’ u ’ , g r i d=g r i d , s p a c e o r d e r =2 , t i m e o r d e r =2)

Aqui, um espa¸co de um metro no eixo x e um metro no y foram divididos em 21 partes, e a fun¸c˜ao criada representa u(t, x, y).

´

E poss´ıvel, ent˜ao, criar a equa¸c˜ao diferencial parcial da onda usando a segunda derivada no tempo e o operador laplaciano, ambos fornecidos em forma simb´olica pelo Devito.

(36)

Ainda, ´e necess´ario criar uma vari´avel para a velocidade c que, aqui, ser´a dada como 1 por fins de simplicidade aritm´etica. Assim, temos:

pde = ( 1 / c ∗ c ) ∗ u . dt2 − u . l a p l a c e

Finalmente, para concluir esta primeira etapa e dar abertura `a pr´oxima, ´e preciso transformar a equa¸c˜ao diferencial parcial em um estˆencil, em uma equa¸c˜ao que representa o novo estado da fun¸c˜ao no pr´oximo intervalo de tempo.

Para isso devemos criar uma equa¸c˜ao onde seu lado esquerdo representa o novo estado na dimens˜ao do tempo, e seu lado direito representa o rearranjo da equa¸c˜ao diferencial parcial em respeito `a esse novo estado. Isso seria, para o exemplo dado acima, respecti-vamente:

u(t + dt, x, y) (6.2)

1.0 ∗ dt2∗ (−2.0 ∗ u(t, x, y) + u(t, x, y − hy) + u(t, x, y + hy) h2

y

+−2.0 ∗ u(t, x, y) + u(t, x − hx, y) + u(t, x + hx, y) h2

x

+2.0 ∗ u(t, x, y) − 1.0 ∗ u(t − dt, x, y)

dt2 )

(6.3)

Novamente, com uso do Devito, ´e poss´ıvel escrever tal equa¸c˜ao de forma muito mais sucinta e compreens´ıvel, de modo que ao final desta primeira etapa, temos:

s t e n c i l = Eq ( u . f o r w a r d , s o l v e ( pde , u . f o r w a r d ) )

6.2

Tradu¸

ao da DSL com Sympy

Nesta etapa, almeja-se traduzir a representa¸c˜ao simb´olica do estˆencil obtido na etapa anterior em uma express˜ao com indexamento expl´ıcito. Pode-se dizer, ent˜ao, que deseja-se reproduzir parte do comportamento do objeto “Operator” do Devito, fazendo uso do SymPy.

Para executar essa tarefa, implementou-se uma classe chamada “Parser”, ou seja, um analisador sint´atico, que lˆe a representa¸c˜ao em alto n´ıvel da equa¸c˜ao e gera a representa¸c˜ao correspondente em baixo n´ıvel.

Nesta tradu¸c˜ao, as duas ferramentas indispens´aveis s˜ao o pr´oprio SymPy, j´a introdu-zido neste documento, e o Regex, ou express˜oes regulares.

Esta ferramenta, dispon´ıvel em in´umeras linguagens de programa¸c˜ao e at´e em busca-dores de palavras em editores de texto, permite que quaisquer sequˆencias de caracteres

(37)

desejadas sejam identificadas em uma outra sequˆencia de caracteres, normalmente uma frase, um par´agrafo, ou um texto inteiro. Essa ferramenta permite, por exemplo, identi-ficar todos os n´umeros em um texto, ou todas as palavras que come¸cam por certa letra, ou at´e mesmo por¸c˜oes inteiras que incluem determinado padr˜ao de caracteres.

Descrever minuciosamente como essa ferramenta funciona n˜ao conv´em aos objetivos deste documento. Por´em os padr˜oes de identifica¸c˜ao usados no analisador sint´atico ser˜ao devidamente descritos, assim como o motivo de seu uso.

A primeira coisa que o Parser faz ´e transformar o estˆencil em uma string, ou seja, uma cadeia de caracteres. No exemplo anterior, obt´em-se:

Eq ( u ( t + dt , x , y ) , 1 . 0 ∗ dt ∗∗2∗( −2.0∗ u ( t , x , y ) / h y ∗∗2 + u ( t , x , y − h y ) / h y ∗∗2 + u ( t , x , y + h y ) / h y ∗∗2 − 2 . 0 ∗ u ( t , x , y ) / h x ∗∗2 + u ( t , x − h x , y ) / h x ∗∗2 + u ( t , x + h x , y ) / h x ∗∗2 + 2 . 0 ∗ u ( t , x , y ) / dt ∗∗2 − 1 . 0 ∗ u ( t − dt , x , y ) / dt ∗ ∗ 2 ) )

Em seguida, deve-se identificar os s´ımbolos livres do estˆencil, isto ´e, aqueles s´ımbolos que deveriam, mas ainda n˜ao est˜ao, atrelados a uma vari´avel espec´ıfica que represente este s´ımbolo. No presente caso, os s´ımbolos livres s˜ao: ‘h y’, ‘x’, ‘y’, ‘dt’, ‘t’ e ‘h x’. O s´ımbolo ‘u’ n˜ao ´e uma vari´avel livre, pois ele j´a est´a vinculado a uma vari´avel. A lista de s´ımbolos ´e facilmente obtida com uma fun¸c˜ao do Devito origin´aria de uma fun¸c˜ao de mesmo nome do SymPy.

Dado esse preparo, ´e poss´ıvel atacar de fato a tradu¸c˜ao da express˜ao do Devito em uma express˜ao de indexamento expl´ıcito. E isso se faz, antes, com a tradu¸c˜ao do Devito em uma express˜ao puramente SymPy, sem as abrevia¸c˜oes sint´aticas que o Devito proporciona. A raz˜ao de se realizar esta opera¸c˜ao, ao inv´es de realizar uma tradu¸c˜ao direta, ´e que o SymPy, como j´a descrito, possui uma fun¸c˜ao que transforma a express˜ao simb´olica diretamente em c´odigo C. Em outras palavras, assim que se obtiver a express˜ao em alto n´ıvel em formato SymPy, ´e poss´ıvel gerar a express˜ao de baixo n´ıvel com uma ´unica chamada da fun¸c˜ao ‘ccode’.

A tradu¸c˜ao Devito-SymPy possui 3 partes:

1. Substituir as fun¸c˜oes

2. Substituir os s´ımbolos livres

3. Substituir os n´umeros decimais, ou floats

A primeira substitui¸c˜ao utiliza o padr˜ao Regex u\((.*?)\). Isso quer dizer que ele identificar´a todas as fun¸c˜oes u(...), n˜ao importa seu conte´udo. Al´em disso, cada fun¸c˜ao

(38)

identificada ser´a substitu´ıda pela string do seu equivalente SymPy, o objeto Element descrito anteriormente. Essa transforma¸c˜ao ´e necess´aria, pois a fun¸c˜ao ‘ccode’ n˜ao suporta o atual estado do estˆencil.

Deve-se adicionar que nesta substitui¸c˜ao ´e realizada a solu¸c˜ao de um problema que, se n˜ao feita aqui, exigiria mais processamento p´ostumo.

Do jeito que o Regex est´a formulado, busca-se a fun¸c˜ao completa, mas na hora da substitui¸c˜ao pode-se facilmente trabalhar ou com a fun¸c˜ao como um todo, ou com seus parˆametros. Isso ´e necess´ario para se declarar o elemento como “Element(’u’, parame-ters.split(’, ’)), o que nos devolve, por exemplo, “Element(u, indices=(t, h x + x, y))”.

Acontece que os termos ‘h x’, ‘h y’, e ‘dt’, enquanto ´ındices da fun¸c˜ao, fazem parte da equa¸c˜ao apenas em sua express˜ao de alto n´ıvel. Por outro lado, durante o indexamento expl´ıcito, deseja-se poder acessar as posi¸c˜oes de um vetor multidimensional uma a uma.

Quando a fun¸c˜ao foi criada com base em uma grade, j´a se deixou impl´ıcito que cada ponto no espa¸co seria separado por uma distˆancia de h x e h y em cada eixo. Portanto, ao se transformar a equa¸c˜ao em um vetor multidimensional, um incremento de uma unidade no ´ındice de cada dimens˜ao representaria exatamente esse passo, representado por esses s´ımbolos. Em outras palavras, em vez de se usar u[t][x + h x][y], por exemplo, usa-se u[t][x + 1][y].

Assim, todos os s´ımbolos que representam um passo em alguma dimens˜ao devem ser transformados no n´umero 1. Para o exemplo, obt´em-se:

Eq ( Element ( u , i n d i c e s =( t + 1 , x , y ) ) , 1 . 0 ∗ dt ∗ ∗ 2 ∗ ( −2.0∗ Element ( u , i n d i c e s =(t , x , y ) ) / h y ∗∗2 + Element ( u , i n d i c e s =(t , x , y − 1 ) ) / h y ∗∗2 + Element ( u , i n d i c e s =(t , x , y + 1 ) ) / h y ∗∗2 − 2 . 0 ∗ Element ( u , i n d i c e s =(t , x , y ) ) / h x ∗∗2 + Element ( u , i n d i c e s =(t , x − 1 , y ) ) / h x ∗∗2 + Element ( u , i n d i c e s =(t , x + 1 , y ) ) / h x ∗∗2 + 2 . 0 ∗ Element ( u , i n d i c e s =(t , x , y ) ) / dt ∗∗2 − 1 . 0 ∗ Element ( u , i n d i c e s =( t − 1 , x , y ) ) / dt ∗ ∗ 2 ) )

A segunda substitui¸c˜ao utiliza o padr˜ao Regex “\w+”. Isso quer dizer que ele identi-ficar´a todas as palavras compostas somente pelas letras do alfabeto. Aqui ´e que entram os s´ımbolos livres identificados anteriormente, pois verifica-se se cada palavra est´a entre os s´ımbolos e, em caso positivo, a palavra identificada ser´a substitu´ıda pela string do seu equivalente SymPy, o objeto Symbol descrito anteriormente.

(39)

quaisquer vari´aveis, nˆao se pode avaliar a string em uma express˜ao que possa ser convertida em c´odigo C pela fun¸c˜ao “ccode”.

Ao fim desta opera¸c˜ao, obt´em-se:

Eq (

Element ( u , i n d i c e s =(Symbol ( ’ t ’ ) + 1 , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) ) ) , 1 . 0 ∗ Symbol ( ’ dt ’ ) ∗ ∗ 2 ∗ (

−2.0∗ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) ) ) / Symbol ( ’ h y ’ ) ∗ ∗ 2

+ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) − 1 ) ) / Symbol ( ’ h y ’ ) ∗ ∗ 2

+ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) + 1 ) ) / Symbol ( ’ h y ’ ) ∗ ∗ 2

− 2 . 0 ∗ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) ) ) / Symbol ( ’ h x ’ ) ∗ ∗ 2

+ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) − 1 , Symbol ( ’ y ’ ) ) / Symbol ( ’ h x ’ ) ∗ ∗ 2

+ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) + 1 , Symbol ( ’ y ’ ) ) ) / Symbol ( ’ h x ’ ) ∗ ∗ 2

+ 2 . 0 ∗ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) ) ) / Symbol ( ’ dt ’ ) ∗ ∗ 2

− 1 . 0 ∗ Element ( u , i n d i c e s=

( Symbol ( ’ t ’ ) − 1 , Symbol ( ’ x ’ ) , Symbol ( ’ y ’ ) ) / Symbol ( ’ dt ’ ) ∗ ∗ 2 ) )

A terceira, e ´ultima, substitui¸c˜ao utiliza o padr˜ao Regex “\d+\.\d+”. Isso que dizer que ele identificar´a todos os n´umeros decimais, ou seja, aqueles separados por um ponto. Al´em disso, cada n´umero identificado ser´a substitu´ıdo pela string do seu equivalente SymPy, o objeto Float, que representa, naturalmente, o tipo “float” de n´umeros decimais. Esta ´ultima substitui¸c˜ao pode parecer sup´erflua, por´em sem ela o c´odigo n˜ao funciona

Referências

Documentos relacionados

■ Uma forma mais l´ ogica de se escrever as equa¸c˜ oes de Maxwell ´e colocar todos os termos com os campos no lado esquerdo das equa¸c˜ oes, enquanto que as cargas e correntes

grandiflora por estaquia, foram avaliados dois ambientes (viveiro e ambiente / condições de ocorrência natural), assim como o efeito do hormônio de enraizamento, o ácido

Estando o processo formalmente em ordem, e havendo possibilidade legal de se proceder à contratação, ratifico a inexigibilidade de licitação, nos termos do artigo 25, inciso III,

Se ele for atˆ omico, classifique-o como express˜ ao e propriedade ou mais de uma ex- press˜ ao e rela¸c˜ ao, destacando as express˜ oes, propriedades e rela¸c˜ oes

Com isso, alguns objetivo foram tra¸ cados tais como: o estudo te´ orico e a implementa¸ c˜ ao num´ erica de m´ etodos aplicados ` a resolu¸ c˜ ao de Sistemas de Equa¸ c˜ oes n˜

A figura 20 ilustra o fluxo para concep¸c˜ ao do modelo prim´ ario utilizando regras de an´ alise t´ ecnica, conforme descrito na se¸c˜ ao 3.2, este modelo ´ e utilizado para

próteses polirnerizadas por energia de microondas e pelo método convencional. Associado a essa variável, foi utilizado Micro Liquid nas resinas. Foram feitas

Um dos campos abaixo n˜ ao pode ser de natureza