计算实体中大概日期的出现次数

时间:2015-09-16 09:20:59

标签: java list date java-ee objectify

我需要在用户选择的持续时间内计算图表的点数。

我的图表是关于日志的,我们需要知道在特定持续时间内每指定分钟连接的用户数。我们不想使用太多查询,所以我主要使用列表。

日期以字符串格式存储为" yyyy-MM-dd HH:mm:ss"。

我的代码有效但加载时间太长了:

    old=ofy().load().type(Log.class).filter("site in",selectedSites).filter("license in",ofy().load().type(License.class).filter("name", name)).filter("date_out >=",datemin).filter("date_out <=",datemax).list();

    Duration duration = new Duration(firstIn, lastDateOut); //Duration between two dates choosen by the user
    int dimension=(int) ((duration.getStandardMinutes())/divideBy); //Number of abscissa points in the chart
    DateTime[] dates=new DateTime[dimension+1]; //Init of the dates 
    int[] counts=new int[dimension+1]; //Init of the count table (count of logged users at the date
    DateTime transfert=firstIn; //First date 


    for(int i=0;i<=dimension;i++){
        counts[i]=0;
        dates[i]=transfert.minusSeconds(transfert.getSecondOfMinute());
        transfert=transfert.plusMinutes(divideBy);
        for(Log log:old){
            if((StaticMethods.toDateTime(log.getDate_in()).minusSeconds(StaticMethods.toDateTime(log.getDate_in()).getSecondOfMinute()).equals(dates[i]))
                ||((StaticMethods.toDateTime(log.getDate_in()).minusSeconds(StaticMethods.toDateTime(log.getDate_in()).getSecondOfMinute()).isBefore(dates[i]))
                        &&(StaticMethods.toDateTime(log.getDate_out()).minusSeconds(StaticMethods.toDateTime(log.getDate_out()).getSecondOfMinute()).isAfter(dates[i])))
                ||(StaticMethods.toDateTime(log.getDate_out()).minusSeconds(StaticMethods.toDateTime(log.getDate_out()).getSecondOfMinute()).equals(dates[i]))
            ){
                counts[i]++;
            }
        }
        GraphData nw=new GraphData(dates[i].toDate(), counts[i]);
    }

我想知道是否可能有更少的加载时间(已阅读this,我需要知道是否有类似的近似值方式。)

1 个答案:

答案 0 :(得分:0)

您应首先按Date_out值按升序排序数据。此外,您不需要日期和计数表,请尝试以下

Duration duration = new Duration(firstIn, lastDateOut); //Duration between two dates choosen by the user
int dimension=(int) ((duration.getStandardMinutes())/divideBy); //Number of abscissa points in the chart
DateTime transfert=firstIn; //First date
DateTime currentDate=transfert; // X-Axis Date
int currentCount=0; // Y-Axis LoggedUser Count

//Log data
DateTime log_DateIn;
DateTime log_DateOut;

for(int i=0;i<=dimension;i++)
{
   currentDate = transfert;
   currentCount = 0;
   transfert = transfert.plusMinutes(divideBy);

   for(Log log:old)
   {
      // We store our dates into variables, that way we avoid doing the time conversion twice
      log_DateIn = StaticMethods.toDateTime(log.getDate_in()).minusSeconds(StaticMethods.toDateTime(log.getDate_in()).getSecondOfMinute());

      log_DateOut = StaticMethods.toDateTime(log.getDate_out()).minusSeconds(StaticMethods.toDateTime(log.getDate_out()).getSecondOfMinute());

      // Since we made the list ordered by DateOut, we are sure that if the stored DateOut is greater than transfert we can't find another user, that way we can break the for without parsing each log
      if(log_DateOut.isAfter(transfert))
         break;

      // Now we can do checks to see if we need to increase the count
      // We just check if the DateIn is between the currentDate and currentDate + divideBy (transfert)
      if(log_DateIn.isAfter(currentDate) && log_DateIn.isBefore(transfert))
         currentCount++;
      // Same thing for DateOut
      else if(log_DateOut.isAfter(currentDate) && log_DateOut.isBefore(transfert))
         currentCount++;
      // Now we need both cases
      else if(log_DateIn.isBefore(currentDate) && log_DateOut.isAfter(transfert))
         currentCount++;
      // Equalities
      else if(log_DateIn.equals(currentDate) || log_DateIn.equals(transfert) || log_DateOut.equals(currentDate) || log_DateOut.equals(transfert))
         currentCount++;
   }

   GraphData nw = new GraphData(currentDate, currentCount);
}