Geração Automática de Código Android Eficiente a
partir de Modelos UML
Abilio Gambim Parada, Aline Rodrigues Tonini, Lisane Brisolara de Brisolara
Ciência da Computação, Grupo de Arquiteturas e Circuitos Integrados,
Centro de Desenvolvimento Tecnológico,
Universidade Federal de Pelotas, Brasil
{agparada, artonini, lisane}@inf.ufpel.edu.br
Resumo. Dispositivos móveis vêm substituindo computadores para uma série
de aplicações. Um grande número destes aparelhos utilizam a plataforma
Android da Google. Este crescimento na utilização de dispositivos móveis tem
impulsionado o mercado de desenvolvimento de aplicações para estes
dispositivos. Entretanto, devido ao curto tempo de lançamento do produto no
mercado, abordagens que visam acelerar o desenvolvimento são necessárias.
Para diminuir o tempo de desenvolvimento e ao mesmo tempo suportar projetos
complexos, abordagens de engenharia baseada em modelos, ou MDE (ModeldrivenEngineering), estão sendo utilizadas. No entanto, os desenvolvedores
devem se preocupar também em atender requisitos não funcionais relacionadas
a desempenho e consumo de energia inerentes ao domínio. Neste contexto, a
Google propôs um conjunto de boas práticas e técnicas de programação para
aplicações Android, tendo como principal objetivo o desempenho das
aplicações. Este artigo propõe uma abordagem MDE para geração automática
de código, a qual aplica boas práticas Android, visando à geração de código
eficiente. A abordagem é demonstrada através de um estudo de caso, no qual a
melhoria obtida com as práticas adotadas pode ser observada.
Palavras Chaves: Android, UML, boas práticas, desempenho, geração de
código, MDE.
1 Introdução
A crescente utilização de dispositivos móveis, como smartphones e tablets, tem se
tornado uma alternativa à utilização de computadores de uso pessoal, impulsionado
assim o mercado destes eletrônicos. Dentre as várias plataformas disponíveis no
mercado surge a plataforma Android [1], como uma solução completa de código livre
com um amplo suporte aos mais diversos dispositivos, bem como ferramentas de
apoio ao desenvolvimento e sistema operacional.
Aplicativos Android trazem novas características para a programação tanto no
estilo quanto em peculiaridades que devem ser observadas. Uma destas características
é a programação orientada a eventos, pois estes aplicativos devem constantemente
reagir a interações do usuário [2], e também conceitos adicionais como ciclo de vida e
a utilização de determinada estrutura de acordo com o comportamento da
aplicação.Estas novas características aumentam a dificuldade do desenvolvimento de
aplicativos Android. Além disso, desenvolvedores devem se preocupar também com a
eficiência e um melhor aproveitamento dos recursos do dispositivo. Considerando
estas particularidades e o fato de existir pessoas de vários lugares do mundo com
maneiras diferentes de programar desenvolvendo aplicações para Android, a Google
propõe o uso de “Boas Práticas” no processo de desenvolvimento [3], para assim
viabilizar um melhor desempenho das aplicações Android.
Além de todas as características de desenvolvimento e de boas práticas que devem
ser consideradas, as aplicações Android estão fortemente ligadas ao mercado
possuindo um curto tempo de desenvolvimento. Tradicionalmente, abordagens de
Engenharia Dirigida por Modelos ou MDE (do inglês, Model Driven Engineering)
vem sendo adotadas, principalmente por que oferecem abstração através do uso de
modelos e automação através de transformação de modelos, facilitando e acelerando o
desenvolvimento [4]. Segundo um estudo realizado na Motorola, a MDE pode reduzir
em até 70% o tempo de produção de software [5].
Entretanto o uso efetivo do paradigma MDE no desenvolvimento Android, requer
uma abordagem dedicada para a modelagem dos aplicativos e ferramentas capazes de
transformar modelos UML em código Android. Para resolver este problema, em [6],
foi proposta uma abordagem para modelagem e geração de código. Entretanto esta
abordagem não aplica técnicas de otimização de código, dessa forma, este artigo
estende esta abordagem para a geração de código Android eficiente através da
aplicação das boas práticas propostas pela Google. Nossa abordagem é demonstrada e
os resultados de desempenho são discutidos através de um estudo de caso.
Este artigo está organizado da seguinte forma. A Seção 2 apresenta a
fundamentação teórica, enquanto a Seção 3 apresenta e discute trabalhos
relacionados. Na seção 4, a abordagem proposta para geração de código eficiente é
detalhada e o estudo de caso que demonstra resultados de seu emprego é apresentado
na Seção 5. As conclusões do trabalho são discutidas na Seção 6.
2
Boas práticas Android
A Google sugere uma série de “Boas Práticas” para o desenvolvimento de aplicativos
Android. Estas boas práticas são dicas simples de programação que aplicadas aos
hábitos de codificação proporcionam um melhor desempenho geral da aplicação. Esta
seção introduz estas boas práticas bem como destaca o seu impacto no desempenho,
segundo o estudo realizado pela Google em [3].
Uma das boas práticas indicadas pela Google é evitar a criação de objetos
desnecessários, pois a criação destes é sempre custosa. A alocação de objetos em
excesso faz com que a coleta de lixo seja realizada periodicamente, o que tem um
impacto negativo no desempenho da aplicação.
Outra prática sugerida é preferir o uso de métodos estáticos ao invés de virtuais.
Desta forma, métodos que não irão acessar campos do objeto devem ser declarados
como estáticos. De acordo com o estudo da Google, invocações estáticas serão de
15% a 20 % mais rápidas.
Neste conjunto de boas práticas, é recomendado o uso de static final para
constantes, pois ao usar a palavra reservada final na definição de constantes os
acessos serão mais rápidos. Isso se deve ao fato da classe não requerer o método
<clinit>, visto que constantes são armazenadas em um campo do arquivo .dex
responsável pela inicialização das constantes. Porém, esta recomendação é válida
somente para tipos primitivos e Strings constantes.
Em linguagens orientadas a objeto como C++ e Java é comum o uso de getter para
acessar atributos ao invés de acessá-los diretamente. Porém esta não é uma prática
recomendável para Android, pois as chamadas a métodos virtuais são muito mais
caras do que o acesso direto ao campo. Desta forma, é recomendado que o uso de
getters e setters seja evitado. De acordo com a Google, o tempo para acessar um
atributo diretamente é três vezes mais rápido do que através de um getter sem o
recurso de JIT (Just-in-time) e cerca de sete vezes mais rápido com o uso do JIT.
A sintaxe do for aprimorado ou for-each pode ser usada para definir coleções que
implementam uma interface iterativa para Arrays. Com as coleções é alocado um
iterador que faz chamadas a hashNext e next. De acordo com a Google o uso da
sintaxe aprimorada do for em Arrays é três vezes mais rápido (com ou sem o uso de
JIT) comparado com o uso do for com iterador explícito.
É possível iterar uma matriz de três maneiras, como mostram os trechos de código
abaixo. A maneira como zero itera a matriz é mais lenta, pois o JIT não otimiza a
maneira de obter o comprimento da matriz a cada iteração do laço. A iteração usada
em one é mais rápida, pois utiliza variáveis locais e o comprimento da matriz oferece
um beneficio de desempenho. A implementação da sintaxe aprimorada do for,
introduzida no Java 1.5, realizada em two é a mais rápida em dispositivos sem JIT e
indiferente de one para dispositivos com JIT. É possível iterar uma matriz de três
maneiras, como mostra o trecho de código abaixo:
Códigos com várias implementações de for
static class Foo {
intmSplat;
}
Foo[] mArray = ...
public void zero(){
int sum = 0;
for (int i = 0; i<mArray.length;
sum + = mArray[i].mSplat;
}
}
++i){
public void one(){
int sum = 0;
Foo[] localArray = mArray;
intlen = localArray.length;
for (int i = 0; i<len; ++i){
sum + = localArray[i].mSplat;
}
}
public void two(){
int sum = 0;
for( Foo : a ){
sum + = a.mSplat;
}
}
As boas práticas também indicam o uso de acesso do tipo pacote (package) ao
invés do tipo privado (private) em classes internas privadas. Esta prática se aplica
quando uma classe interna a outra (inner class) precisa acessar atributos da classe
externa. A máquina virtual considera o acesso direto da classe interna a membros
privados da classe externa como sendo ilegal, porque são classes diferentes. Para
evitar esse problema atributos e métodos que devem ser acessados por classes internas
devem ter visibilidade do tipo pacote, indicada pelo modificador public, protected ou
sem nenhum modificador [7]. Ao aplicar a prática sugerida, evita-se uma sobrecarga
em aplicações que utilizam classes internas em pontos críticos de desempenho. Outra
boa prática é evitar o uso de Ponto Flutuante, pois de acordo com a Google, o seu uso
em dispositivos Android é cerca de duas vezes mais lento do que o uso de inteiros.
3 Trabalhos Relacionados
Muitos trabalhos preocupam-se com a eficiência de aplicações para dispositivos
móveis [8][9][10]. Em [8] os autores discutem a sobrecarga no desempenho induzida
pelo uso da abstração em camadas para software embarcado, usando como plataforma
alvo o Android. Em [9], um conjunto de benchmarks foram implementados de
diferentes formas no Android e avaliados quanto ao desempenho. Os resultados
mostraram uma sobrecarga do Java-Android comparado a implementações C rodando
na mesma plataforma. Da mesma forma, em [10] são realizados experimentos com
diferentes implementações de algoritmos e são analisados resultados de desempenho e
energia consumida pelas implementações quando executadas no Android. Porém,
nenhum destes trabalhos considera as boas práticas. Apenas em [11] o impacto destas
práticas no desempenho do software foi avaliado através de experimentos.
Como este ainda é um campo de atuação novo, há um número bastante reduzido de
ferramentas que proveem a geração automática de código para dispositivos Android a
partir de modelos de alto nível de abstração. A IBM recentemente adicionou à
ferramenta Rational Rhapsody [12] um perfil para aplicações Android. No entanto,
sua abordagem exige que a aplicação seja definida em um nível baixo de detalhe para
que a geração de código seja realizada. Além da IBM, observam-se esforços da
Google e da Eclipse. A Google propôs o App Inventor [13] e a Eclipse, o AndroMate
[14], ambas focam na modelagem gráfica e geração para Android. No entanto, tanto o
AndroMate como o App Inventor poderiam ser classificados como programação
visual ao invés de orientados a modelos. Ainda deve-se ressaltar que nenhuma destas
abordagens considera boas práticas ou inclui passos de otimização no momento da
geração de código. Nossa abordagem difere-se das abordagens utilizadas por estas
ferramentas, pois procura minimizar os detalhes que devem ser inseridos pelo
projetista no modelo e aplica boas práticas automaticamente durante a geração de
código, suportando assim a geração de código eficiente para a plataforma Android.
4
Geração de Código Android Eficiente
A geração automática de código Android eficiente proposta neste trabalho baseia-se
na aplicação das boas práticas propostas pela Google para dispositivos Android.
Assim como proposto em [6], nossa abordagem gera código Java-Android a partir de
modelos UML construídos usando suas notações padrão, sendo esta transformação
suportada por uma ferramenta em desenvolvimento pelo grupo. Durante a geração de
código, a ferramenta aplica as boas práticas, visando a obtenção de código otimizado
para a plataforma Android, evitando que o projetista tenha que refatorar o código para
incluir estas otimizações manualmente. Estas otimizações são opcionais de forma que
o usuário pode escolher quais otimizações serão aplicadas, para assim observar os
impactos destas otimizações de forma isolada.
A entrada da ferramenta de geração de código é um modelo UML, composto de
diagramas de classe e de sequência, construídos de acordo com a abordagem
apresentada em [6]. O diagrama de classe oferece a visão estrutural, a partir da qual
código estrutural pode ser gerado. Já os diagramas de sequência são usados na
geração de código comportamental. A Seção 4.1 apresenta a geração estrutural de
código eficiente para a plataforma Android, enquanto a geração comportamental é
detalhada na Seção 4.2. Atualmente, nossa ferramenta implementa três das boas
práticas sugeridas pelo Google. Destas, uma afeta apenas a geração estrutural, outra
apenas a geração comportamental e outra modifica ambas as gerações.
4.1
Geração Estrutural
Na geração de código estrutural, são geradas definições de atributos (nome, tipo e
visibilidade), de métodos (nome, parâmetros e visibilidade) e importação de pacotes.
Duas das boas práticas são aplicadas na geração do código estrutural.
A primeira delas se refere a geração dos atributos e se baseia na boa prática que
sugere o uso dos modificadores static e static final para constantes. Quando um
atributo tem um valor de inicialização, este é classificado como constante pela
ferramenta. Neste caso, a ferramenta aplica a boa prática, gerando a declaração com o
modificador mais apropriado. Se a constante for do tipo primitivo ou String, é usado o
static final, caso contrário, apenas o modificador static é usado. Esta boa prática traz
benefícios na velocidade de acesso a estas constantes, proporcionando assim um
melhor desempenho para o sistema, como discutido na Seção 2.
A segunda boa prática aplicada na geração refere-se à definição e geração de
métodos de acesso a atributos, os métodos getters e setters. Na primeira versão da
ferramenta, sem foco na otimização, para todo o atributo era gerado um método getter
e um método setter, mesmo que estes métodos não estivessem explicitados no modelo
da classe. No entanto, esta prática é contrária a uma das boas práticas do Google que
propõe o acesso direto aos atributos sem métodos getters e setters como forma de
melhorar o desempenho do código. A eliminação destes métodos pode requerer
mudanças na visibilidade do atributo para permitir que o mesmo seja acessado
diretamente, e também a eliminação da invocação do método de acesso. Desta forma,
esta boa prática não afeta apenas a geração do código estrutural, mas também afeta a
geração de código comportamental (discutida na Seção 4.2).
Na geração estrutural, nossa ferramenta realiza a análise dos atributos e métodos
de acesso descritos no modelo antes da geração propriamente dita do código. Caso
seja identificado um atributo privado (private ou protect) para o qual métodos de
acesso tenham sido definidos no modelo, a ferramenta irá gerar a definição do
atributo como público (public) e não fará a definição dos métodos de acesso
correspondentes. Para isto é necessário que o projetista siga a boa prática indicada
para programação em geral, de utilizar nomes para métodos de acesso contendo o
nome do atributo a ser acessado [15] com prefixo get ou set.
4.2
Geração Comportamental
Na geração do código comportamental das aplicações Android, a aplicação da boa
prática de eliminação de chamadas aos métodos getters e setters deve ser concluída.
Para tal, a ferramenta deve analisar os diagramas de sequência para identificar onde
são utilizados estes métodos de acesso, para posteriormente substituir a invocação do
método por uma atribuição ou leitura do atributo.
Neste trabalho, também propomos a aplicação da boa prática relativa à utilização
da sintaxe do for apropriada, apresentada na Seção 2. Para aplicação desta boa prática,
a ferramenta deve analisar os diagramas de sequência do modelo, com especial
atenção naqueles onde um fragmento do tipo loop é usado, o qual representa uma
iteração. A análise para determinar a melhor sintaxe do for considera o que está sendo
utilizado dentro da estrutura de iteração.Caso seja iterado uma coleção de objetos é
indicado pelas boas práticas a utilização da sintaxe for-each, enquanto que para a
manipulação de um simples vetor é indicado a utilização do for-lenght. Desta forma,
com base nas características do modelo, a ferramenta escolhe a melhor sintaxe de
acordo com as boas práticas para o uso do for apresentadas na Seção 2.
5
Estudo de Caso
Para demonstrar a nossa abordagem bem como os resultados obtidos pelo uso das
boas práticas, esta seção apresenta um estudo de caso. Neste estudo, primeiramente, a
aplicação Snake é modelada em UML, seguindo a nossa abordagem de modelagem
proposta em [6] e realizando a engenharia reversa do código original da aplicação.
Posteriormente, este modelo é usado como entrada para a ferramenta GenCode, a qual
gera o código a aplicação. A aplicação escolhida está disponível no site de apoio ao
desenvolvedor Android [16]. Apesar de ser uma aplicação simples, ela permite a
demonstração dos principais aspectos da abordagem, bem como apontar as melhorias
alcançadas com a aplicação das boas práticas.
Neste estudo é demonstrada a geração de trechos de código da aplicação, focando
nos pontos do código onde as práticas foram aplicadas. Primeiramente, será
demonstrada a aplicação da eliminação de getters e setters, que conforme explicado
na Seção 4, é realizada pelas duas rotinas de geração de código, estrutural e
comportamental. Após, será demonstrada a aplicação da boa prática do for. Para
facilitar a visualização das melhorias aplicadas pela geração, o código original será
comparado com o código automaticamente gerado pela ferramenta. O código gerado
inclui a aplicação de boas práticas (em separado) e a comparação entre estes dois
códigos permite observar o impacto das otimizações. Além disso, análises de
desempenho também foram realizadas, permitindo a comparação entre os códigos.
A Figura 1 ilustra a visão estática da aplicação, representada pelo diagrama de
classes. Nesta figura são destacadas as classes Activity, View e Handler, pertencentes
ao Android. A partir das informações obtidas neste diagrama, o código estrutural foi
gerado. Como a eliminação de getters e setters foi habilitada, a ferramenta realizou a
análise de atributos e de seus métodos de acesso. Esta busca identificou o método
setTextView da classe Snake, contexto onde a boa prática que evita getters e setters
deveria ser aplicada. Abaixo, são apresentados os trechos do código original e do
código gerado, após a captura e análise do diagrama. O código original define o
atributo como privado (modificador private) e declara o método de acesso, bem como
o corpo deste método. Já o código gerado automaticamente declara este atributo como
público (usando o modificador public) e não faz a declaração do método setTextView.
Fig. 1. Diagrama de classe, representação estrutural da aplicação Snake.
Trecho de código original da aplicação Snake utilizando setter
private TextView textView;
public void setTextView(TextView textView) {
this.textView = textView;
}
Trecho de código da aplicação Snake utilizando a prática que evita getters e setters
public TextView textView;
Para a eliminação do método setTextView, porém, a ferramenta realizou uma busca
entre os diagramas de sequência a fim de identificar onde este método era invocado.
Para então, substituir esta invocaçãopor uma atribuição. Sem a otimização, o código
que seria gerado a partir do modelo comportamental, incluiria a invocação do método
setTextView(), conforme trecho de código abaixo.
Trecho de código original da classe SnakeView, invocação do método de acesso
mSnakeView.setTextView(findViewById(R.id.text));
Enquanto que com a aplicação da boa prática, a rotina de geração do código
comportamental faz a busca pela invocação do método a ser eliminado e substitui a
sua chamada pelo acesso direto ao atributo, gerando o trecho de código abaixo.
Trecho de código da classe SnakeView, utilizando a prática que evita getters e setters
mSnakeView.textView = findViewById(R.id.text);
Para a comparação da eficiência do código gerado pela nossa ferramenta com o
código original do aplicativo, foi utilizada a ferramenta DDMS (Dalvik Debug
Monitor Server) [17], que fornece resultados relativos ao tempo de execução de
códigos Android. A DDMS gera CPU Include Time, o qual considera o tempo de
execução do método analisado incluindo o tempo dos métodos chamados por este, e o
CPU Exclude Time, que por sua vez, considera apenas o tempo de execução do
método em análise. Todos os experimentos realizados e discutidos nesta seção foram
repetidos 30 vezes, e a partir dos tempos de execução obtidos, uma média foi
calculada, a qual é utilizada nas comparações realizadas.
Os resultados obtidos pela análise de desempenho dos dois códigos são
apresentados no gráfico ilustrado na Fig. 2, onde o eixo y representa o tempo da CPU
em milissegundos (ms). Esta análise de desempenho considera o CPU Include Time
fornecido pela DDMS, pois o custo da chamada do método de acesso deve ser
contabilizado, neste caso. O tempo médio de execução do fragmento do código
original (Fig. 2) foi de 0,8444 ms e o desvio padrão foi de 0,0276 ms, enquanto o
tempo de execução do código gerado foi de 0,8030 ms e o desvio padrão de 0,30 ms.
Foi utilizado o teste estatístico “t de student” para comparação de médias, sendo a
diferença entre as médias considerada estatisticamente significativa. Neste gráfico,
observa-se que o tempo de execução foi reduzido em 4,9029% pela aplicação da boa
prática que evita o uso de getters e setters, o que demostra o impacto real da
utilização desta boa prática.
Incl CPU Time (ms)
Comparação Com Setter - Sem Setter
0,88
0,86
0,84
0,82
0,8
0,78
0,76
0,74
0,72
Com Setter
Sem Setter
Fig. 2. Gráfico representando a diferença de desempenho na utilização de métodos de acesso.
Neste estudo de caso, a aplicação da boa prática da escolha da sintaxe do for
também é demonstrada. Esta boa prática é tratada apenas pela rotina de geração de
código comportamental. Durante esta rotina, laços devem ser identificados nos
diagramas de sequência. Para demonstrar sua aplicação é usada a representação de
uma pequena parcela do modelo comportamental do Snake ilustrado na Figura 3. Este
diagrama de sequência se refere ao detalhamento do método enqueueDirection
proveniente da classe SnakeView. Neste diagrama pode-se observar o uso de um laço
de iteração no qual o objeto mNextDirectionArray é iterado. O laço é representado
pelo fragmento loop. Outro fragmento interno a este, do tipo opt, representa uma
condicional, que restringe a invocação do método add(direction).
Fig. 3. Diagrama de sequência do método enqueueDirection da classe SnakeView.
Com base nas informações contidas neste diagrama, a ferramenta aplica a boa
prática e determina qual a sintaxe apropriada para a implementação da manipulação
do Array mNextDirectionArray. Neste caso, a ferramenta escolhe o uso do for-each,
devido ao uso de um Array junto a um laço. Abaixo são apresentados os
fragmentosreferente ao laço. No código original o for normal é usado, enquanto no
código gerado pela ferramenta, o for-each é usado.
Trecho de código original da aplicação Snake, utilizando a sintaxe normal do for
private void enqueueDirection(int direction) {
int c=mNextDirectionArray.size();
for (int i=0; i<c; i++) {
if (mNextDirectionArray.get(i)==0) {
mNextDirectionArray.add(i,direction);
break;
}
}
}
Trecho de código gerado aplicando a boa prática do for-each
private void enqueueDirection(int direction) {
for (Integer c : mNextDirectionArray) {
if (c.equals(0)) {
mNextDirectionArray.add(direction);
break;
}
}
}
Para demonstrar a melhoria em desempenho obtida pela aplicação desta
otimização, foram realizados experimentos após a geração do código (considerando
apenas esta otimização). Os resultados de desempenho do código original e código
gerado são ilustrados no gráfico da Fig. 4. A análise de desempenho neste caso,
considera o CPU Exclude Time fornecido pela DDMS, pois apenas o custo do laço
deve ser contabilizado, não incluindo o custo da chamada do método addDirection().
Pode-se observar que o tempo médio de execução com o for normal (código original)
foi de 59,0882 mscom desvio padrão de 1,5526 ms, enquanto o resultado utilizando o
for-each (código gerado), foi de 12,4501ms, tendo o desvio padrão de 0,5249 ms.
Valores médios de tempo de execução foram usados nestacomparação e a diferença
entre as médias também foi considerada estatisticamente significativa.
Excl CPu Time (ms)
Comparação For Normal - For Each
70
60
50
40
30
20
10
0
For Normal
For - Each
Fig. 4. Desempenho obtido pelo for normal e pelo for-each
6 Conclusões
Este artigo apresenta uma abordagem MDE para geração automática de código
Android eficiente a partir de modelos UML. A geração de código aplica
automaticamente boas práticas do Google, com o objetivo de melhorar o desempenho
do código gerado. Esta geração foi prototipada em uma ferramenta de geração de
código chamada GenCode [6]. A automatização destas otimizações evita que o
projetista tenha de estudar as boas práticas e refatorar o código implementado para
que este faça uso destas práticas e, portanto, tenha o desempenho melhorado. A
abordagem é demonstrada com um estudo de caso, que também é usado para
evidenciar as melhorias no desempenho obtidas com a geração de código proposta.
Além da eficiência do código gerado, outros benefícios podem ser vinculados ao
emprego desta abordagem, dentre estes destaca-se a abstração oferecida pelo uso de
modelos UML e a automação provida pela ferramenta de geração. Além disso, a
abordagem proposta utiliza notações padrão da UML, o que evita a necessidade do
uso de uma ferramenta de modelagem específica.
O uso do diagrama de sequência limita a geração de código comportamental
proposta até o nível de chamada de métodos, que é o que pode ser expresso neste
diagrama. Para obter código completo, outros diagramas precisam ser considerados na
geração de código. Atualmente, nossa ferramenta implementa três das boas práticas
sugeridas pelo Google. Como trabalhos futuros, pretendemos analisar a viabilidade de
estender esta abordagem para outras boas práticas, priorizando aquelas que
apresentam maior impacto no desempenho.
Referências
1.Google. (2012) Fundamentos de uma aplicação Android. Disponível em:
http://developer.android.com/guide/components/fundamentals.html. Acesso em: Dezembro,
2012.
2.Kraemer, F. A. et al., “Engineering android applications based on UML activities”,
Proceedings of the 14th international conference on Model driven engineering languages
and systems (MODELS’11), Jon Whittle, Tony Clark, and Thomas Khne (Eds.). SpringerVerlag, Berlin, Heidelberg, pp. 183–197, 2011.
3.Google.
(2012)
Boas
práticas
para
performance.
Disponível
em:
http://developer.android.com/training/best-performance.html. Acesso em: Dezembro, 2012.
4.Selic, B. “Models, software models, and UML”, UML for real: Design of embedded real time
systems, vol. Boston: Kluwer Academic Publishers, pp. 1–16, 2003.
5.Weigert, T. “Practical experiences in using model-driven engineering to develop
trustworthy,” Computing Systems. IEEE International Conference on Sensor Networks,
Ubiquitous, and Trustworthy Computing, vol. 1 (SUTC’06), 2011.
6.Parada, A., Brisolara, L.: A model driven approach for Android application development.
SBESC, Brazilian Symposium on Computing System Engineering, Natal, 2012.
7.Oracle. (2012) Controlling Access to Members of a Class.
http://docs.oracle.com/javase/tutorial/java/javaOO/accesscontrol.html.
Dezembro, 2012.
Disponível
Acesso
em:
em:
8.Camara, V. B., Corrêa, U. B. Performance Overhead from the Usage of Software Abstraction
on Complex Embedded Systems. SBESC, Brazilian Symposium on Computing System
Engineering, Florianópolis, 2011.
9.Batyuk, L., et al. (2009) “Developing and Benchmarking Native Linux Applications on
Android” in Mobile Wireless Middleware, Operating Systems, and Applications. 2009.
10.Vieira et al. Análise de desempenho e consumo energético para aplicações embarcadas na
Plataforma Android. SBESC, Brazilian Symposiumon Computing System Engineering,
Natal, 2012.
11.Beckmann, M. Avaliação das Boas Práticas de Codificação para Plataforma Android.
Trabalho de conclusão de curso. UFPel.
12.IBM.
(2012)
Rational
Rhapsody.
Disponível
http://www.ibm.com/software/awdtools/rhapsody/. Acesso em: Dezembro, 2012.
em:
13.MIT. (2012) App Inventor. Disponível em: http://appinventor.mit.edu/. Acesso em:
Dezembro, 2012.
14.Telematica Instituut. (2012) The android modeller and code generator. Disponível em:
http://www.lab.telin.nl/_msteen/andromate/. Acesso em: Dezembro, 2012.
15.Martin, R..: Clean Code: A hand book of Agile Software Craftsmanship, , Pearson, Boston,
(2009).
16.Google.
(2012)
Exemplos
de
Aplicações
Android
http://developer.android.com/tools/samples/index.html. Acesso em: Dezembro, 2012.
em:
17.Google.
(2012)
Using
DDMS.
Disponível
em:
http://developer.android.com/tools/debugging/ddms.html. Acesso em: Dezembro, 2012
Download

Geração Automática de Código Android Eficiente a partir de