[RESOLVIDO XD]Uma ajudinha aqui xDDD - Performace?

6 respostas
P

Boa dia galera,

Estou no meio de um trabalho e enfrento uma seria dificuldade. Como principal funcao no meio trabalho eu faço muitas somas com datas e horas (vide exemplo do calendario do google) . Porem nao enxergo uma maneira de desenvolver o meu algoritmo para gerar esses horarios escolhidos e gravar no banco.

Exemplo.: Eu qro que durante um certo período, supondo do dia 1 de outubro ate dia 15, de segunda a sexta, fique marcado no meu calendario apartir das 8am ate as 18, compromissos q tem periodos de 1 em 1 hora (ai em cima desses compromissos as pessoas vao poder reservar essa hora), com exeção do 12:00 dia. Ai tem q aparecer no meu calendario esses dias marcados com esses horarios em destaque para as pessoas marcarem.

Minha duvida é: Devo usar o JODA TIME que dizem q é uma api muito boa para ser usadas somas de datas e horas, ou uso a DATE, ou entao uso a API do Google que é super confusa?

Sobre a api do google eu encontrei essas informações, mas nao consegui implementar nd ainda.


http://code.google.com/apis/calendar/developers_guide_protocol.html#ManagingCalendars
http://code.google.com/support/bin/answer.py?answer=78455

Também tentei começar uma função do banco de dados, chegaram a me falar q essa regra seria bem trabada no meu BD. Entao fiz um script ± assim:

SELECT to_char(sysdate + 1/24*rownum, 'DD HH24:Mi')
  FROM user_objects
 WHERE sysdate < '10/10/2008';

A ideia dessa procedure é que eu busque todas as datas q eu qro e fazer um insert delas mesmo (o insert ainda nao fiz é claro), mas nao posso rodar isso no bd por causa desse from q nao é indicado pra usar ne, é so um gambi mesmo.

Alguem pode me ajudar a dar uma luz, pelo menos em relação a API q uso, ou se uso o banco de dados e como conseguiria fazer isso no banco ± (melhorando o meu script).
Ah sim, no meu trabalho eu to usando o JQuerry Calendar!

Obrigadaa ^^

6 Respostas

B

Dê uma olhada no próprio código da Joda, vendo como ele se relaciona com Date dá pra tirar uma idéia de como guardar períodos no banco.

P

Entao, consegui gerar ± os horarios em formato de TIMESTAMP pra colocar no banco de dados, segue o codigo:

public class Horarios {
	
	/*
	 * diaIni    = Dia de inicio, 
	 * diaFin    = Dia final
	 * mesIni    = Mes de inicio
	 * mesFin    = Mes final
	 * anoIni    = Ano de inicio
	 * anoFin    = Ano final
	 * horaIni   = Hora de inicio
	 * minIni    = Minuto da hora de inicio
	 * horaFin   = Hora final
	 * minutoFin = Minuto da hora de final
	 */	
	
	/*Ano no formado AAAA (int)
	Mes nao pode ter o '0' na frente*/
	
	
	public static void main (String args[]){
		Horarios.geraTodaSemana1Hora(1,7,1,11,2008,2009,1,1,5,1); // aqui faco um teste
	}	
	/**** Minuto de inicio deve ser o mesmo do minuto final *****/
	public static ArrayList<Horario> geraTodaSemana1Hora(int diaIni, int diaFin, int mesIni, int mesFin, int anoIni, int anoFin, int horaIni, int minIni, int horaFin, int minFin){
		for (int a=anoIni; a<=anoFin; a++){ 
			ArrayList<Horario> list = new ArrayList<Horario>();
			String mes, timestamp;
			String hora;
			String minuto;
			String dia;
			for(int m=mesIni; m<=mesFin; m++){	
				for (int d=diaIni; d<=diaFin; d++){
					for (int h=horaIni; h<=horaFin; h++){
						for(int min=minIni; min<=minFin; min++){
							if(m<10) {
								mes = "0" + m;
							}else {
								mes = "" + m;
							}
							if(h<10) {
								hora = "0" + h;
							}else {
								hora = "" + h;
							}
							if(min<10) {
								minuto = "0" + min;
							}else {
								minuto = "" + h;
							}
							if(d<10) {
								dia = "0" + d;
							}else {
								dia = "" + d;
							}
							//forma arraylist de beans, retor o arraylist<horario>
							String timestamp = a+"-"+ mes +"-"+dia+" " + hora +":" + minuto +":00";
							Horario h = new Horario();
							h.setTimestamp(timestamp);
							list.add(h);
						}
					}
				}
			}
		}
	}
}

O script ainda nao ta 100% pq aind nao to controlando os dias q tem 30 ou 31 dias ou ano bissexto, mas o foco agora é q eu acho q esse codigo ta meio porco e acho q meu professor de estrutura de dados vai cair em cima do meu projeto, alguem tem alguma ideia pra melhorar isso??
Pensei em usar recursividade, mas to meio perdida no meu ponto de parada.

ps.: Nesse algoritmo eu gero entre duas datas diferentes (em anos diferente) todo o dia 1 a 7 de Janeiro ate Novembro em 2008 e 2009 um time stamp da 1:00hr as 5:00 hrs, q vai de hora em hora. (isso é bem o tipo de funcao q eu gero no meu projeto)

Valew ^^

B

Exemplo do que pode ser feito:

Horarios.java
package horarios;

import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.List;

public class Horarios
{
   static Calendar cal = Calendar.getInstance();
   static Calendar cal2 = Calendar.getInstance();

   public static void main(String[] args)
   {

      Horarios h = new Horarios();

      SimpleDateFormat sdf = new SimpleDateFormat("dd/MM/yyyy HH:mm");
      Date dataInicial, dataFinal, horaInicial, horaFinal;
      dataInicial = dataFinal = horaInicial = horaFinal = null;

      try
      {
         dataInicial = sdf.parse("25/01/2008 00:00");
         dataFinal = sdf.parse("05/02/2008 00:00");
         horaInicial = sdf.parse("01/01/2008 08:00");
         horaFinal = sdf.parse("01/01/2008 09:45");
      }
      catch (ParseException ex)
      {
      }

      List list = h.listaDeIntervalosEntre(dataInicial, dataFinal, horaInicial, horaFinal);

      System.out.println(list);
   }

   public List<Intervalo> listaDeIntervalosEntre(Date dataInicial, Date dataFinal, Date horaInicial, Date horaFinal)
   {
      if (! (dataFinal.compareTo(dataInicial) >= 0))
         throw new RuntimeException("Data final deve ser maior ou igual à data inicial");

      if (! (horaFinal.compareTo(horaInicial) > 0))
         throw new RuntimeException("Hora final deve ser maior que a hora inicial");

      List<Intervalo> list = new ArrayList<Intervalo>();

      Date agora = setHora(dataInicial, horaInicial);
      Date fim = setHora(dataFinal, horaFinal);

      while (agora.before(fim))
      {
         Date fimHoje = setHora(agora, horaFinal);

         while (agora.before(fimHoje))
         {
            Date antes = agora;

            // agora mais uam hora
            agora = proximaHora(agora);

            // trata horas incompletas
            if (agora.after(fimHoje))
               agora = fimHoje;

            Intervalo intervalo = new Intervalo(antes, agora);
            list.add(intervalo);
         }

         // vai para amanhã...
         agora = proximoDia(agora);
         // na hora inicial
         agora = setHora(agora, horaInicial);
      }

      return list;
   }

   private Date proximaHora(Date data)
   {
      cal.setTime(data);
      cal.add(Calendar.HOUR_OF_DAY, 1);

      return cal.getTime();
   }

   private Date proximoDia(Date data)
   {
      cal.setTime(data);
      cal.add(Calendar.DAY_OF_MONTH, 1);

      return cal.getTime();
   }

   private Date setHora(Date data, Date hora)
   {
      cal.setTime(data);
      cal2.setTime(hora);
      cal.set(Calendar.HOUR_OF_DAY, cal2.get(Calendar.HOUR_OF_DAY));
      cal.set(Calendar.MINUTE, cal2.get(Calendar.MINUTE));
      cal.set(Calendar.SECOND, cal2.get(Calendar.SECOND));
      cal.set(Calendar.MILLISECOND, cal2.get(Calendar.MILLISECOND));

      return cal.getTime();
   }
}
Intervalo.java
package horarios;

import java.util.Date;

public class Intervalo implements Comparable<Intervalo>
{
   private Date inicio;
   private Date fim;

   public Intervalo(Date inicio, Date fim)
   {
      super();
      if (inicio == null || fim == null)
         throw new IllegalArgumentException("Ambas as datas de inicio e fim não devem ser nulas.");
      if (!(fim.compareTo(inicio) > 0))
         throw new IllegalArgumentException("A data final deve ser maior que a inicial.");

      this.inicio = inicio;
      this.fim = fim;
   }

   public Date getInicio()
   {
      return inicio;
   }

   public Date getFim()
   {
      return fim;
   }

   public int compareTo(Intervalo outroIntervalo)
   {
      // intervalo antes do outro
      // | |
      //     | |
      if (fim.compareTo(outroIntervalo.getInicio()) <= 0)
         return -1;

      // intervalo depois do outro
      //     | |
      // | |
      if (inicio.compareTo(outroIntervalo.getFim()) >= 0)
         return 1;

      int i = inicio.compareTo(outroIntervalo.getInicio());
      int j = fim.compareTo(outroIntervalo.getFim());

      // inicio antes do outro inicio, e fim antes do outro fim
      // |   |
      //   |   |
      if (i < 0 && j < 0)
         return -1;

      // inicio depois do outro inicio, e fim depois do outro fim
      //   |   |
      // |   |
      if (i > 0 && j > 0)
         return 1;

      // se os intervalos forem iguais
      // |  |
      // |  |
      if (i == 0 && j == 0)
         return 0;

      // outros casos serão um intervalo dentro do outro
      // se os inicios forem iguais, antes é quem finaliza primeiro
      if (i == 0)
         return j;

      // todos os outros casos, antes é quem começa primeiro
      return i;
   }

   @Override
   public boolean equals(Object obj)
   {
      if (obj == null)
         return false;
      if (getClass() != obj.getClass())
         return false;
      final Intervalo other = (Intervalo) obj;
      if (this.inicio != other.inicio && (this.inicio == null || !this.inicio.equals(other.inicio)))
         return false;
      if (this.fim != other.fim && (this.fim == null || !this.fim.equals(other.fim)))
         return false;
      return true;
   }

   @Override
   public int hashCode()
   {
      int hash = 3;
      hash = 79 * hash + (this.inicio != null ? this.inicio.hashCode() : 0);
      hash = 79 * hash + (this.fim != null ? this.fim.hashCode() : 0);
      return hash;
   }

   @Override
   public String toString()
   {
      return inicio + " - " + fim;
   }
}
P

Opa adorei!! Brigadão!!

Mas so mais umas duvidazinas xD:

  • ele imprime no formato “Fri Jan 25 09:00:00 GMT-03:00 2008”.
    Eu consigo passar exatamente dessa forma para o banco de dados?? Na verdade eu nao sei se eu consigo jogar isso no banco no formato Date. Por isso tinha pensado em colocar no tipo TimeStamp(q eu conheco) mas nao acho uma forma de passar esse formato para Time Stamp.
  • O dateFormat consegue fazer passar isso para TimeStamp?

Estou usando banco de dados Oracle e Mysql.

Valew ^^

B

Como é um intervalo, ele possui dois valores, data e hora de início e fim. Pegue ambos com getInicio e getFim.

Para transformar de java.util.Date para java.sql.Timestamp, use
Date data = intervalo.getInicio();

Timestamp ts = new Timestamp(data.getTime());
Se quiser crie métodos que retornem Timestamp dentro da classe Intervalo.
P

Ahhhh Brigadao Bruno!!! Me ajudou pra caramba!!!
Funciona perfeitamente aqui, adaptei algumas coisas!
Agora so falta descobrir como eu faço pra passar de meia em meia hora, 15 minutos e etc, pq eu vi q nao aceita tipo Double la no proximaHora.

Mas isso eu tento descobrir sozinha :wink:

Brigadao!! ^^

Criado 15 de outubro de 2008
Ultima resposta 21 de out. de 2008
Respostas 6
Participantes 2