Desenvolvedor e Analista de Sistemas | IFPA

domingo, 3 de março de 2013

Java - Trabalhando com Datas

com 0 Comentário

Quem nunca teve que manipular datas em algum programa não é um programador poxa… O pior caso na minha opinião são aqueles bancos de dados desgraçados que não aceitam a data no formato padrão. Cá entre nós, é uma encheção de saco ficar invertendo a data. Vamos então a algumas dicas para não haver mais traumas quando o assunto em questão são as datas:
Componentes Swing para trabalhar com datas

Nesse outro post eu mostrei como adicionar ao Netbeans alguns ótimos componentes para quem precisa tratar datas de uma maneira elegante em uma interface bem bonita.
Vale a pena dar uma conferida!

Strings de formatação de datas


Algo que todo mundo deve saber é que em alguns componentes (como os demonstrados no post citado acima) e alguns objetos (que veremos mais adiante) conseguem formatar a data de acordo com uma string, ou seja, mostrar a data em diversos formatos, tais quais definidos por uma string.
Antes de mostrar alguns exemplos vou deixar especificado quais os caracteres que podem compor a string de formatação e o que eles representam.
Segundo a documentação oficial:
LetterDate or Time ComponentPresentationExamples
GEra designatorTextAD
yYearYear1996; 96
MMonth in yearMonthJuly; Jul; 07
wWeek in yearNumber27
WWeek in monthNumber2
DDay in yearNumber189
dDay in monthNumber10
FDay of week in monthNumber2
EDay in weekTextTuesday; Tue
aAm/pm markerTextPM
HHour in day (0-23)Number0
kHour in day (1-24)Number24
KHour in am/pm (0-11)Number0
hHour in am/pm (1-12)Number12
mMinute in hourNumber30
sSecond in minuteNumber55
SMillisecondNumber978
zTime zoneGeneral time zonePacific Standard Time; PST; GMT-08:00
ZTime zoneRFC 822 time zone-0800
Fique a vontade para brincar de combinar esses caracteres para formar a data.
Exemplo:
StringData formatadaComentário
dd/MM/yyyy25/12/2010Padrão brasileiro
MM/dd/yyyy12/25/2010Padrão americano
yyyy-MM-dd2010-12-25Padrão de alguns bancos de dados
dd MMMMMMMM yyyy25 Dezembro 2010Quando tem mais de 2 caracteres ‘M’, o resultado é o nome do mês por extenso
HH:mm:ss:SSSS15:22:54:1264Hora…

O objeto SimpleDateFormat: convertendo datas facilmente


A classe SimpleDateFormat do pacote java.lang.text é uma mão na roda tão grande!! Com um objeto dessa classe a gente pode facilmente converter um objeto java.util.Date para uma String no formato que a gente quiser (através da string de formatação).
Exemplo:
SimpleDateFormat sd = new SimpleDateFormat(“yyyy-MM-dd”);
Date data = new Date(); //data atual
 
System.out.println(sd.format(data));
Do mesmo jeito que dá pra converter um objeto Date pra uma String, o inverso também é válido: o SimpleDateFormat também converte uma String para um Date:
SimpleDateFormat sd = new SimpleDateFormat(“dd/MM/yyyy”);
String meuNiver =13/04/1989;
 
Date data = sd.parse(meuNiver);
Muito muito muito simples, útil e prático!

Comparando datas


Não sei se todo mundo sabe… mas uma data representada pelo objeto Date nada mais é do que um long, um número bem grande que guarda o número de milisegundos que já se passaram desde 1º de Janeiro de 1970, 00:00:00 GMT até o mome
nto atual.
O objeto Date possui alguns métodos para comparar datas, são eles:
Date natal = new Date(110,11,25);        //25/12/2010
Date meuNiver = new Date(110,3,13);  //13/04/1989
 
if (natal.after(meuNiver) || meuNiver.before(natal)) {
    System.out.println("Vou ficar mais velho antes do natal...");
} else if (natal.equals(meuNiver)) {
    System.out.println("Vou ganhar 2 presentes no mesmo dia! :D");
}
O código é totalmente auto-explicativo, exceto pelo construtor meio estranho do objeto Date. Seus parâmetros são: o ano – 1900 , o mês – 1, e o dia.
Os métodos “after(Date)”, “before(Date)” e “equals(Object)” nada mais fazem do que comparar aqueles números que eu comentei ali em cima. Quem não acreditar em mim é só ir no código fonte do método (no Netbeans: Ctrl + clique no método) e verificar que é exatamente isso que acontece:
public boolean after(Date when) {
    return getMillisOf(this) > getMillisOf(when);
}
Um probleminha que me ocorreu esses dias (e deu um trabalhinho) foi: como comparar datas sem envolver as horas, minutos, segundos e milisegundos?
Algumas vezes o horário pode atrapalhar a comparação das datas, uma vez que ela se baseia no número por trás da data. Só para ilustrar o problema segue um exemplinho:
Date inicioNatal = new Date(1293242400000L); //25/12/2010 00:00:00
Date fimNatal = new Date(1293328799999L);   //25/12/2010 23:59:59
 
if (inicioNatal.equals(fimNatal)){
    System.out.println("É natal!!");
}
No construtor dos Date foram passados os números que representam o primeiro e último segundo do natal. O “L” no final é apenas para indicar que aquele número é do tipo long.
Voltando ao problema, no código acima nunca será exibida a mensagem “É Natal!!” pois os números que representam as datas não são iguais.
A alternativa para solucionar esse problema que eu achei (confesso que parece uma gambiarra) foi a seguinte:
SimpleDateFormat sd = new SimpleDateFormat("dd/MM/yyyy");
Date inicioNatal = new Date(1293242400000L); //25/12/2010 00:00:00
Date fimNatal = new Date(1293328799999L);   //25/12/2010 23:59:59
 
inicioNatal = sd.parse(sd.format(inicioNatal));
fimNatal = sd.parse(sd.format(fimNatal));
 
if (inicioNatal.equals(fimNatal)){
    System.out.println("É natal!!");
}
As linhas em negrito são responsáveis por “zerar” as horas, minutos, segundos e milisegundos da data.
Como? Muito simples: como o objeto SimpleDateFormat foi criado com uma string de formatação que não contém horas, minutos ou outros, ele simplesmente ignora essas partes da data na hora de converter uma string para Date. Nós primeiro passamos de Date para string (somente dia/mes/ano) e passamos a string para Date em seguida (sem horas, minutos e etc).
Existem muito mais coisas quando se trata de manipulação de datas, mas como esse post não tem a finalidade de deixar ensinar TUDO de avançado sobre datas, ficamos por aqui.

+1

0 comentários :

Postar um comentário

Total de visualizações