Java日期比较器问题

时间:2013-02-18 13:59:54

标签: java priority-queue

我遇到按日期整理比较器的问题。日期格式应该是“dd / MM / yyyy”所以我从SQL数据库中调用我的信息,然后通过执行以下操作将字符串转换为日期:

  public void setDeadlineDate(String deadDate) throws ParseException {
        this.d_date = deadDate;
        //convert strings to dates
        formatter = new SimpleDateFormat("dd/MM/yyyy");
        convertedDeadlineDate = (Date)formatter.parse(deadDate);
    }

然后我在下面创建一个get方法来调用我的比较器。我必须举例说明,但奇怪的日期不合适并且比较不对,总是存在差异。

示例1:

  @Override
    public int compare(JobRequest j1, JobRequest j2) {

        if (j1.getConvertedDeadlineDate().before(j2.getConvertedDeadlineDate())) {
            return -1;
        } else if (j1.getConvertedDeadlineDate().after(j2.getConvertedDeadlineDate())) {
            return 1;
        } 
        else {
            return 0;
        }
    } 

示例2:

public int compare(JobRequest j1, JobRequest j2){
return j1.getConvertedDeadlineDate().compareTo(j2.getConvertedDeadlineDate());
}

这两个例子都给了我一些问题,我的优先事项也没有按照我的意愿按顺序排列。 在我的数据库中,它们以2012年12月1日的“01/12/2012”格式保存为varchar,因为它不会让我使用它们的日期函数来使用英文格式。

对我来说是一个更好的方式来转换字符串然后比较或者我错过了什么?

感谢

编辑: 输出订购日期:

  • 05/04/2011
  • 16/12/2012
  • 18/06/2012
  • 17/12/2013
  • 17/12/2013
  • 16/12/2013
  • 17/12/2013
  • 14/08/2012
  • 19/12/2013

我宣布PriortyQueue:

private Comparator<JobRequest> comparator = new JobQueueComparator(); //calls my comparator
    private PriorityQueue< JobRequest> scheduledJobs = new PriorityQueue<JobRequest>(100, comparator);

    public void addJob(JobRequest job) {
        // now add job to priority queue
        scheduledJobs.add(job); // add jobs from the resultset into queue
    }  

scheduledJobs.add(job)只是从结果集填充队列并继续添加到队列,直到读取了数据库中的所有字段,见下文

public void populateQueueFromDB() {
        // create priority queue
        try {
            String url = "jdbc:mysql://localhost:3306/project";
            Connection conn = DriverManager.getConnection(url, "root", "nbuser");

            PreparedStatement stmt = conn.prepareStatement("SELECT user_id,s_date,e_date,d_date,department,projectname,projectapplication,priority,cores,disk_space,analysis FROM booking");
            ResultSet rs;
            rs = stmt.executeQuery();


            //List<JobRequest> jobList = new ArrayList<JobRequest>();

            while (rs.next()) {
                JobRequest job = new JobRequest();
                User user = new User();
                user.setUserID(rs.getString("user_id"));
                job.setUserID(user.getUserID()); // changes the /user id to the job.setuser id so can call for my queue print.
                job.setStartDate(rs.getString("s_date"));
                job.setEndDate(rs.getString("e_date"));
                job.setDeadlineDate(rs.getString("d_date"));
                job.setDepartment(rs.getString("department"));
                job.setProjectName(rs.getString("projectname"));
                job.setProjectApplication(rs.getString("projectapplication"));
                job.setPriority(rs.getInt("priority"));
                job.setCores(rs.getInt("cores"));
                job.setDiskSpace(rs.getInt("disk_space"));
                job.setAnalysis(rs.getString("analysis"));

                schedulerPriorityQueue.addJob( job );

            }
            schedulerPriorityQueue.printQueue();

            conn.close();

        } catch (Exception e) {
            System.err.println("Got an exception! ");
            System.err.println(e.getMessage());
        }

    }

}

PRINT QUEUE:

public void printQueue() {
        for (JobRequest jr : scheduledJobs) {

            System.out.print(jr.getUserID() + "-->");
            System.out.print(jr.getStartDate() + "--START-->");
            System.out.print(jr.getEndDate() + "---END-->");
            System.out.print(jr.getDeadDate() + "--DROP-->");
            System.out.print(jr.getDepartment() + "-->");
            System.out.print(jr.getProjectName() + "-->");
            System.out.print(jr.getProjectApplication() + "-->");
            System.out.print(jr.getPriority() + "--PRIORITY-->");
            System.out.print(jr.getCores() + "-->");
            System.out.print(jr.getDiskSpace() + "-->");
            System.out.println(jr.getAnaylsis());

        }
    }

3 个答案:

答案 0 :(得分:2)

当你执行:for (JobRequest jr : scheduledJobs) { ...时,你实际上使用的是隐式Iterator,它不能保证按优先级顺序返回项目(由比较器定义)。

如上所述,文档说明:

  

这个类及其迭代器实现了所有可选方法   Collection和Iterator接口。迭代器提供   方法iterator()不保证遍历元素   任何特定顺序的优先级队列。如果您需要有序遍历,   考虑使用Arrays.sort(pq.toArray())。

意味着队列中作业的顺序和迭代器的顺序不一定相同。

如果您只需要列出作业,请使用文档中提到的Arrays.sort方法。

如果您想确保您的PriorityQueue正常工作,您必须将其作为一个整体使用,执行以下操作:

while(!scheduledJobs.isEmpty()) {
     ... = scheduledJobs.poll();
     //print, do whatever
}

请记住,这会从队列中删除元素,并且只应用于测试目的,或者根据需要实际处理作业。但是这应该显示实际优先顺序中的日期。

在我看来,对于如何使用PriorityQueue存在一些混淆。我会说常规用例类似于:

  • 将元素添加到队列
  • 定义一个方法来处理队列中的“jobs”(每个元素)
  • 当队列不为空时,使用poll获取每个元素(返回最小的元素),并做任何你需要做的事情。

答案 1 :(得分:0)

PriorityQueue的文档说

  

不保证方法iterator()中提供的迭代器   以任何特定顺序遍历优先级队列的元素。   如果您需要有序遍历,请考虑使用   Arrays.sort(pq.toArray())

http://docs.oracle.com/javase/6/docs/api/java/util/PriorityQueue.html

答案 2 :(得分:0)

这对我很有用:

public class JobRequest implements Comparable<JobRequest> {

    static final DateFormat formatter = new SimpleDateFormat("dd/MM/yyyy");
    Date convertedDeadlineDate;

    Date getConvertedDeadlineDate() {
        return convertedDeadlineDate;
    }

    public JobRequest(String deadDate) {
        try {
            convertedDeadlineDate = (Date) formatter.parse(deadDate);
        } catch (ParseException e) {
            e.printStackTrace();
        }
    }

    @Override
    public int compareTo(JobRequest j) {
        return this.getConvertedDeadlineDate().compareTo(
                j.getConvertedDeadlineDate());
    }

    public static void main(String[] args) {
        List<JobRequest> list = new ArrayList<>();
        list.add(new JobRequest("10/10/2010"));
        list.add(new JobRequest("09/09/2009"));
        list.add(new JobRequest("11/11/2011"));
        list.add(new JobRequest("08/08/2008"));

        Collections.sort(list);

        for (JobRequest j : list) {
            System.out.println(formatter.format(j.getConvertedDeadlineDate()));
        }
    }

}

导致输出结果:

08/08/2008
09/09/2009
10/10/2010
11/11/2011