Subtrair datas com recursos nativos do java

11 respostas
humberto-adm

Olá galera,

Estou com um projeto desenvolvido em java quase pronto, mas preciso realizar uma subtração envolvendo duas datas.
Na tela do sistema tenho dois campos de texto com uma máscara do tipo ##/##/####. Gostaria de realizar a subtração destas datas para obter o intervalo em dias.

E aproveitando a mensagem, gostaria de sabre as classes do API que trabalham com data. Já conheço Date e Calendar.

[]s, Obrigado

11 Respostas

ViniGodoy

São só essas duas. E são péssimas. Não é à toa que muita gente prefere usar a JODA-Time:
http://joda-time.sourceforge.net/

Eu recomendo fortemente que você use.

sergiotaborda

humberto-adm:
Olá galera,

Estou com um projeto desenvolvido em java quase pronto, mas preciso realizar uma subtração envolvendo duas datas.
Na tela do sistema tenho dois campos de texto com uma máscara do tipo ##/##/####. Gostaria de realizar a subtração destas datas para obter o intervalo em dias.

E aproveitando a mensagem, gostaria de sabre as classes do API que trabalham com data. Já conheço Date e Calendar.

Só existem essas duas… mas java é uma linguagem de programação (pun intended).
Isso significa que vc pode criar as suas proprias classes para manipular datas e tempos. Isto não significa que é fácil…

Substrair duas datas não é um processo matemático no sentido que vc não pode simplesmente subtrair cada campo da data.
É por isso que deve usar Calendar para fazer calculos. (estamos num cenário onde apenas pode usar classes padrão)

Você tem que tender como fazer esses calculos e para isso vc precisa entender os conceitos relacionados à medição do tempo em java. Neste link vc encontra uma implementação de um método que calcula o numero de dias entre duas datas.

humberto-adm

Bom eu estou tentando implementar um classe para realizar esta operação mas esta consumindo tempo no projeto.
ViniGodoy você poderia me passar como eu poderia subtrair duas datas do tipo 2010/05/26 e 2010/05/30 utilizando o JODA - Time.
Eu ja tenho um método que remove as barras da data e se precisar fazer isto eu utilizo ele para elas ficarem assim: 20100526 e 20100530.

Se puder me ajudar eu agradeço muito pq tenho que entregar este projeto semana que vem na faculdade.

[]s, Obrigado

ViniGodoy

Tem um exemplo logo na página inicial do JodaTime:

return Days.daysBetween(fromDate, newYear);
marlon.carvalho

humberto, é possível fazer. Existe este cálculo na biblioteca Alfred (http://alfredlibrary.org), no utilitário CalculoData. Se a ideia é verificar quantos dias existem entre duas datas, então você pode usar a biblioteca desta forma:

CalculoData.calcularDiferencaDias(data1,data2,true);

Mas, se não quer anexar a biblioteca ao seu projeto, você pode verificar como foi implementado aqui:
http://www.alfredlibrary.org/maven/xref/index.html

Basta achar a classe que mencionei.

sf.marcius

usa 2 Dates.

long difEmMsegs = dateMaior.getTime() - dateMenor.getTime();

depois converte pra dias:

1 dia = 24 hs
1h = 60 mins
1min = 60 segs
1 seg = 1000 msegs

logo

int difEmDias = (int) ((difEmMsegs/1000)/3600)/24;

vc pode criar uma classe DateHelper por ex e colocar nela os metodos utilitários para datas que tu criar.
eu pelo menos fiz isso. :slight_smile:

[]s

sergiotaborda

sf.marcius:
usa 2 Dates.

long difEmMsegs = dateMaior.getTime() - dateMenor.getTime();

depois converte pra dias:

1 dia = 24 hs
1h = 60 mins
1min = 60 segs
1 seg = 1000 msegs

logo

int difEmDias = (int) ((difEmMsegs/1000)/3600)/24;

vc pode criar uma classe DateHelper por ex e colocar nela os metodos utilitários para datas que tu criar.
eu pelo menos fiz isso. :slight_smile:

Errrr… Isto é exatamente como vc não deve fazer!

@humberto-adm , cara pelo menos leia as referencias que damos. Se vc tivesse lido o link que passei vc encontrava este método

public int daysBetween(Date start, Date end){
  
       if (start.compareTo(end) < 0){
            throw new IllegalArgumentException("Data inicial tem que ser maior ou igual à final");
       } else if (start.compareTo(end)==0){
           return 0; // É o mesmo dia.
       }
         
        Calendar calendar = (Calendar) referenceCalendar.clone();
       calendar.setTime(toDateOnly(start));
         
        Date endDate = toDateOnly(end);
        
        int count =0;
        while (calendar.getTime().compareTo(endDate)!=0){
            calendar.add(Calendar.DATE, 1);
            count++;
        }
         
       return count;
 }
sf.marcius

que existem melhores meios de se fazer isso, como usando o Joda Time por exemplo, isso eu sei…

mas pq aquilo que fiz é o modo como não se deve fazer?

veja bem que o colega ta dizendo que as datas vêm de text fields com máscara “##/##/####”, logo o parse dos dates não conterão infos de hora. também colocou no título “recursos nativos”, por isso nao disse de cara o “Joda”.

usando um mesmo SimpleDateFormat pra fazer o parse dos dois campos, não fará diferença a localização (ambos terão a mesma).

o caso do colega é simples.
o algorítmo que postei é simples e fácil de entender.

qual o caso que ele não da certo nessas condições?

Obs: estou perguntando na humildade:)

[]s

sergiotaborda

sf.marcius:
sergiotaborda:

Errrr… Isto é exatamente como vc não deve fazer!

que existem melhores meios de se fazer isso, como usando o Joda Time por exemplo, isso eu sei…

mas pq aquilo que fiz é o modo como não se deve fazer?

Porque o tempo contado em milisegundos não é proporcional ao tempo corrido em dias. Por exemplo, se o ano é bissexto o tempo em milesgundos corrido desde 27 de fevereiro a 1 de março é o mesmo que corrido de 28 a 1 se o ano não é bissexto. Existem muitas peculiaridades e por isso que temos a classe calendar para cuidar disso. Depois a conversão para dias e meses é simplista, dependendo do ano e do calendário , ela pode não estar certa. Portanto, é melhor usar o algoritmo que funciona sempre, e esse é aqule que exemplifiquei, vai somando um dia, até chegar na data que se quer. Repare que não é uma questão de melhor e pior. O seu método não dá resultados corretos, logo ele nem sequer uma opção.

humberto-adm

A solução que eu usei no meu projeto foi essa, deu certo, eu tinha pensado neste tipo de método, obrigado
[]s

sf.marcius:
usa 2 Dates.

long difEmMsegs = dateMaior.getTime() - dateMenor.getTime();

depois converte pra dias:

1 dia = 24 hs
1h = 60 mins
1min = 60 segs
1 seg = 1000 msegs

logo

int difEmDias = (int) ((difEmMsegs/1000)/3600)/24;

vc pode criar uma classe DateHelper por ex e colocar nela os metodos utilitários para datas que tu criar.
eu pelo menos fiz isso. :slight_smile:

[]s

humberto-adm

Vou procurar usar a biblioteca JODA, parece ser fácil.
E qualquer dúvida eu posta aqui no fórum…
Vlw pela dica pessoal
[]s

Criado 26 de maio de 2010
Ultima resposta 29 de mai. de 2010
Respostas 11
Participantes 5