• Nenhum resultado encontrado

Uma Questão de Estilo Elementos de Estilo Java

N/A
N/A
Protected

Academic year: 2021

Share "Uma Questão de Estilo Elementos de Estilo Java"

Copied!
8
0
0

Texto

(1)

Uma Quest˜ao de Estilo

Elementos de Estilo Java

Vasco. T. Vasconcelos

9 Setembro 2004

Escrevemos programas para serem lidos por humanos. Pelos outros, mas tamb´em por n´os, daqui a uma semana. As linguagens de programac¸˜ao n˜ao vˆem equipadas com regras de estilo. De facto, nada nos impede de escrever um programa completo em apenas uma linha de c´odigo.

No entanto, a comunidade de programadores de uma dada linguagem desenvolve um certo estilo. Um estilo comum favorece a leitura do nosso c´odigo pelos outros programadores, mas, talvez mais importante, torn´a-lo-´a mais robusto, de mais f´acil manutenc¸˜ao, e tender´a a conter menos bugs.

As regras que abaixo enuncio s˜ao baseadas no livro de bolso “The Elements of Java Style” [1], cuja leitura recomendo a todos os estudantes da linguagem Java. Consulte tamb´em as convenc¸˜oes da Sun emhttp://java.sun.com/docs/codeconv/.

1

Formatac¸˜ao de texto

Reflectir no texto do programa a estrutura l´ogica de blocos do programa. Grande parte do c´odigo Java tem a formaX{bloco}que dever´a ser escrito

X { b l o c o } Exemplos: class UmaClasse { void f ( i n t n ) { i f ( n > 0) { f o r ( i n t i = 0 ; i > n ; i ++) { xxx } } } } i f ( j < 0) { xxx } else i f ( j < 0) { xxx } else { xxx }

(2)

Partir linhas demasiado longas. Linhas demasiado longas podem parecer bem no terminal, mas n˜ao quando impressas. Vamos limitar-nos a 80 caracteres por linha, partindo linhas demasiado longas. Exemplos:

double l e n g t h = Math . s q r t ( Math . pow ( x , 2 . 0 ) ,

Math . pow ( y , 2 . 0 ) ;

r e t u r n year < o t h e r . year | |

year = = o t h e r . year & & month < o t h e r . month | |

( year = = o t h e r . year & & month = = o t h e r . month && day < o t h e r . day ) ;

Incluir espac¸os. Utilizar um espac¸o para separar um parˆentesis ‘)’ ou chaveta direita ‘}’ de uma palavra reservada; e uma palavra reservada de um parˆentesis ‘(’ ou chaveta esquerda ‘{’. Exemplos: while . ( ) .{ xxx } i f . ( ) .{ xxx } else . i f . ( ) .{ xxx } else .{ xxx }

Utilizar um espac¸o antes e depois de qualquer operador bin´ario, excepto o ponto ‘.’.

r e t u r n ( daysSince ( FIRST DATE ) + 5 ) % 7 ; r e t u r n Date . isLeapYear ( year ) ? 3 6 5 : 3 6 6 ;

Utilizar uma linha em branco para separar cada membro de uma classe.

p u b l i c class Date { /∗∗ ∗ Ano . ∗/ p r i v a t e i n t year ; /∗ ∗

∗ O ano d est a data .

∗/

p u b l i c i n t getMonth ( ) { r e t u r n month ; }

Evitar utilizar caracteres de tabulac¸˜ao. O n´umero de espac¸os que correspondem a um tab varia de ambiente para ambiente. Um texto correctamente alinhado num ambiente de programac¸˜ao pode aparecer completamente desalinhado noutro.

2

Identificadores

Utilizar nomes sugestivos. Em vez de

(3)

utilizamos

year = FIRST YEAR ;

com a declarac¸˜ao

/∗∗

∗ O ano da p r i m e i r a data .

∗/

p u b l i c s t a t i c f i n a l i n t FIRST YEAR = 1 5 8 2 ;

N˜ao comer vogais. Qual dos dois ´e mais f´acil de ler?

boolean i s L p Y r ( ) { . . . }

boolean isLeapYear ( ) { . . . }

Nomes de classes ou interfaces comec¸am por mai ´uscula.

p u b l i c class P r i n t S t r e a m extends F i l t e r O u t p u t S t r e a m {

xxx

}

Utilizar substantivos para nomes de classes. Classes definem objectos que devem ser identificados por substantivos.

p u b l i c class Date {

xxx

}

Utilizar substantivos ou adjectivos para nomes de interfaces. Utilizar substantivos para nomear interfaces que descrevem servic¸os:

p u b l i c i n t e r f a c e A c t i o n L i s t e n e r {

xxx

}

e adjectivos para descrever competˆencias:

p u b l i c i n t e r f a c e Runnable {

xxx

}

Nomes de m´etodos comec¸am por letra minuscula.

p u b l i c void advanceToWeekDay ( i n t weekDay ) {

xxx

}

Nomes de vari´aveis, de argumentos e de atributos comec¸am por letra min ´uscula.

p r i v a t e i n t year ;

p u b l i c s t a t i c i n t daysInMonth ( i n t year , i n t month ) {

i n t r e s u l t ;

xxx

(4)

Todas as vari´aveis (verresultacima) tˆem o prop´osito de nos auxiliar em c´alculos mais complexos. Chamar aux a uma vari´avel n˜ao ajuda a compreens˜ao do c´odigo. Todas as vari´aveis s˜ao tempor´arias: vivem at´e ao fim do bloco onde foram declaradas. Chamartempa uma vari´avel n˜ao nos ajuda em nada.

Fazer coincidir o nome de um parˆametro com o nome atributo correspondente.

p u b l i c Date ( i n t year , i n t month , i n t day ) {

t h i s . year = year ; t h i s . month = month ; t h i s . day = day ; } p u b l i c void s e t Y e a r ( i n t year ) { t h i s . year = year ; }

Nomes de constantes escrevem-se apenas com mai ´usculas; as v´arias palavras s˜ao separadas por underscore.

p u b l i c s t a t i c f i n a l i n t FIRST YEAR = 1 5 8 2 ;

3

Documentac¸˜ao

• Escrever documentac¸˜ao para quem utiliza o c´odigo; • Escrever documentac¸˜ao para quem mant´em o c´odigo; • Manter o c´odigo e a documentac¸˜ao em sincronia; • Utilizar a voz activa;

• Ser sucinto.

Utilizar cabec¸alhos para descrever classes, interfaces e seus membros.

/∗∗

∗ Datas do c a l e n d ´a r i o Gregoriano ,

∗ r e p r e s e n t a d a s por t r ˆe s i n t e i r o s : ano , mˆes e d i a .

∗/

p u b l i c c l a s s Date {

/∗ ∗

∗ C o n s t r u i r uma data i g u a l `a p r i m e i r a data v ´a l i d a .

∗/ p u b l i c Date ( ) { xxx } xxx }

(5)

Utilizar coment´arios longos para esconder partes de c´odigo, sem o apagar. Porque os coment´arios n˜ao podem ser anichados, coment´arios longos devem ser utilizados ape-nas para esconder c´odigo temporariamente.

/∗

Escondi e s t e c ´o d i g o temporariamente . i f ( day < daysThisMonth ( ) )

day ++;

∗/

Utilizar coment´arios de linha para explicar detalhes de implementac¸˜ao.

p u b l i c i n t weekDay ( ) {

/ / Sabemos que a p r i m e i r a data f o i uma sexta−f e i r a r e t u r n ( daysSince ( FIRST DATE ) + 5 ) % 7 ;

}

4

Programac¸˜ao

Definir m´etodos pequenos. Se um m´etodo tiver mais de 10 linhas, provavelmente cont´em em si mais do que uma rotina. Descubra quais e declare-as separadamente. Em vez de:

p u b l i c void add ( i n t numberOfDays ) {

f o r ( i n t i = 0 ; i <numberOfDays ; i ++) i f ( day < daysThisMonth ( ) ) day ++; else { day = 1 ; i f ( month <1 2 ) month ++; else { month = 1 ; year ++; } } }

escrevemos uma rotina que permite avanc¸ar um dia:

p u b l i c void f o r t h ( ) { i f ( day < daysThisMonth ( ) ) day ++; else { / / U l t i m o d i a do mˆes´ day = 1 ; i f ( month < 1 2 )

month + + ; / / U l t i m o d i a dum mˆes que n ˜ao Dezembro´ e l s e { / / 3 1 de Dezembro month = 1 ; year ++; } } }

e outra que permite avanc¸ar um dado n´umero de dias

p u b l i c void add ( i n t numberOfDays ) {

f o r ( i n t i = 0 ; i <numberOfDays ; i ++) f o r t h ( ) ;

(6)

N˜ao declarar sem inicializar. Evitamos declarar de vari´aveis sem as inicializar. Para isso declaramos as vari´aveis onde precisamos delas, e n˜ao no in´ıcio dos m´etodos. Quando declaramos, inicializamos logo. Em vez de declarar agora e mais tarde atribuir um valor inicial:

i n t a r a b i c ;

. . .

a r a b i c = scanner . n e x t I n t ( ) ;

declaramos e inicializamos mais tarde:

. . .

i n t a r a b i c = scanner . n e x t I n t ( ) ;

Utilizar um ´unico ponto de sa´ıda numa rotina. Em vez de doisreturn:

i f ( Date . isLeapYear ( year ) ) r e t u r n 3 6 5 ;

else

r e t u r n 3 6 6 ;

escrevemos:

r e t u r n Date . isLeapYear ( year ) ? 3 6 5 : 3 6 6 ;

Em vez de quatroreturn:

p u b l i c s t a t i c i n t daysInMonth ( i n t year , i n t month ) {

switch ( month ) {

case 4 : case 6 : case 9 : case 1 1 : r e t u r n = 3 0 ;

case 2 :

i f ( Date . isLeapYear ( year ) ) r e t u r n 2 9 ; else r e t u r n 2 8 ; d e f a u l t : r e t u r n = 3 1 ; } }

declaramos, no in´ıcio da func¸˜ao, uma vari´avel que representa o seu valor. No fim devolvemos o valor desta vari´avel:

p u b l i c s t a t i c i n t daysInMonth ( i n t year , i n t month ) {

i n t r e s u l t ; switch ( month ) {

case 4 : case 6 : case 9 : case 1 1 : r e s u l t = 3 0 ;

break ; case 2 :

r e s u l t = Date . isLeapYear ( year ) ? 2 9 : 2 8 ; break ; d e f a u l t : r e s u l t = 3 1 ; break ; } r e t u r n r e s u l t ; }

(7)

Evitar “Se sim, sim; sen˜ao, n˜ao” As express˜oes s˜ao avaliadas antes de serem uti-lizadas. Em vez de dizer “Se a express˜ao ´e verdadeira, retorno verdade; se a express˜ao ´e falsa, retorno falso”:

i f ( o t h e r . e a r l i e r ( t h i s ) ) r e t u r n t r u e ;

else

r e t u r n f a l s e ;

dizemos “retorno (o valor d)a express˜ao”:

r e t u r n o t h e r . e a r l i e r ( t h i s ) ;

De modo semelhante, em vez de

i f ( o t h e r . e a r l i e r ( t h i s ) ) b = t r u e ; else b = f a l s e ; escrevemos b = o t h e r . e a r l i e r ( t h i s ) ;

Evitarexp == true. A express˜aoexp == true:

i f ( i s V a l i d ( ) = = t r u e ) {

xxx

}

tem exactamente o mesmo valor de verdade do queexp:

i f ( i s V a l i d ( ) ) {

xxx

}

E se forexp == false? eexp != true?

Evitarreturn (exp). A palavrareturn´e reservada da linguagem, n˜ao se trata do nome de uma func¸˜ao. Os parˆentesis mais exteriores dificultam a leitura. Em vez de

r e t u r n ( o t h e r . e a r l i e r ( t h i s ) ) ;

escrevemos

r e t u r n o t h e r . e a r l i e r ( t h i s ) ;

N˜ao esbanjar vari´aveis. A excessiva declarac¸˜ao de vari´aveis dificulta a leitura do c´odigo. Se a vari´avel for utilizada apenas uma vez, substitutimos essa utilizac¸˜ao pela express˜ao de inicializac¸˜ao. Em vez de:

i n t a r a b i c = scanner . n e x t I n t ( ) ;

RomanNumber roman = new RomanNumber ( a r a b i c ) ;

escrevemos

(8)

N˜ao utilizar importac¸˜oes an´onimas. Em vez de

import j a v a . u t i l .∗;

seleccionamos as classes (ou interfaces) que queremos importar:

import j a v a . u t i l . Comparable ; import j a v a . U t i l . Map ;

Deste modo ajudamos o leitor dizendo exactamente quais os tipos em que estamos interessados.

References

[1] A. Vermeulen, S. Ambler, et al. The elements of Java style. Cambridge University Press, 2000. ISBN 0 521 77768 2.

Referências

Documentos relacionados

Recomendação: A elevação da PaCO 2 para valores acima do normal (até 90 mmHg), com pH acima de 7, pode ser tolerada durante a ventilação mecânica na asma, caso

Vogal designado pela Presidente do Centro de Estágio de entre os membros do Conselho Regional de Lisboa: Dr.ª Carla Cristina Machado Rodrigues Dias, Advogada, que usa profissional-

A DWX-4 é ideal para laboratórios de pequeno e médio porte, que ainda não usam ferramentas digitais, ou para aqueles laboratórios com scanners que não desejam mais terceirizar

Outros perigos As zonas potenciais para a superexposição a este produto são a pele e o contato com os olhos Não se espera que a inalação de vapor e a ingestão sejam

O principal objetivo deste artigo é mostrar a viabilidade desta abordagem, visto que não conhecemos a aplicação de algoritmos de ponto interior para a solu- ção de problemas

Considerando o circuito acima, que ilustra um amplificador operacional utilizado para implementar um amplificador de tensão, julgue os itens a seguir.. 62 O amplificador de

Na fachada posterior da sede, na parte voltada para um pátio interno onde hoje há um jardim, as esquadrias não são mais de caixilharia de vidro, permanecendo apenas as de folhas

The need for bodies and jurisdictional entities of the CAs to adopt urgent measures to enable agile, effective and cooperative ways of acquiring equipment’s, services and