001package net.sf.cpsolver.exam.reports; 002 003import java.text.DecimalFormat; 004import java.util.List; 005 006import net.sf.cpsolver.exam.model.Exam; 007import net.sf.cpsolver.exam.model.ExamModel; 008import net.sf.cpsolver.exam.model.ExamPlacement; 009import net.sf.cpsolver.exam.model.ExamStudent; 010import net.sf.cpsolver.ifs.util.CSVFile; 011import net.sf.cpsolver.ifs.util.CSVFile.CSVField; 012 013/** 014 * Export student more than two exams a day conflicts between triplets of exams 015 * into a CSV file. <br> 016 * <br> 017 * Usage:<br> 018 * <code> 019 * new ExamStudentMoreTwoADay(model).report().save(file); 020 * </code> <br> 021 * <br> 022 * 023 * @version ExamTT 1.2 (Examination Timetabling)<br> 024 * Copyright (C) 2008 - 2010 Tomáš Müller<br> 025 * <a href="mailto:muller@unitime.org">muller@unitime.org</a><br> 026 * <a href="http://muller.unitime.org">http://muller.unitime.org</a><br> 027 * <br> 028 * This library is free software; you can redistribute it and/or modify 029 * it under the terms of the GNU Lesser General Public License as 030 * published by the Free Software Foundation; either version 3 of the 031 * License, or (at your option) any later version. <br> 032 * <br> 033 * This library is distributed in the hope that it will be useful, but 034 * WITHOUT ANY WARRANTY; without even the implied warranty of 035 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 036 * Lesser General Public License for more details. <br> 037 * <br> 038 * You should have received a copy of the GNU Lesser General Public 039 * License along with this library; if not see 040 * <a href='http://www.gnu.org/licenses/'>http://www.gnu.org/licenses/</a>. 041 */ 042public class ExamStudentMoreTwoADay { 043 private ExamModel iModel = null; 044 045 /** 046 * Constructor 047 * 048 * @param model 049 * examination timetabling model 050 */ 051 public ExamStudentMoreTwoADay(ExamModel model) { 052 iModel = model; 053 } 054 055 /** 056 * generate report 057 */ 058 public CSVFile report() { 059 CSVFile csv = new CSVFile(); 060 csv.setHeader(new CSVField[] { new CSVField("Exam 1"), new CSVField("Enrl 1"), new CSVField("Period 1"), 061 new CSVField("Date 1"), new CSVField("Time 1"), new CSVField("Exam 2"), new CSVField("Enrl 2"), 062 new CSVField("Period 2"), new CSVField("Time 2"), new CSVField("Exam 3"), new CSVField("Enrl 3"), 063 new CSVField("Period 3"), new CSVField("Time 3"), new CSVField("More-2-Day"), 064 new CSVField("More-2-Day [%]") }); 065 DecimalFormat df = new DecimalFormat("0.0"); 066 for (Exam ex1 : iModel.variables()) { 067 ExamPlacement p1 = ex1.getAssignment(); 068 if (p1 == null) 069 continue; 070 for (Exam ex2 : iModel.variables()) { 071 if (ex2.equals(ex1)) 072 continue; 073 ExamPlacement p2 = ex2.getAssignment(); 074 if (p2 == null || p2.getPeriod().getDay() != p1.getPeriod().getDay() 075 || p2.getPeriod().getIndex() < p1.getPeriod().getIndex()) 076 continue; 077 if (p1.getPeriod().equals(p2.getPeriod()) && ex1.getId() >= ex2.getId()) 078 continue; 079 List<ExamStudent> students = ex1.getJointEnrollments().get(ex2); 080 if (students == null || students.isEmpty()) 081 continue; 082 for (Exam ex3 : iModel.variables()) { 083 if (ex3.equals(ex2) || ex3.equals(ex1)) 084 continue; 085 ExamPlacement p3 = ex3.getAssignment(); 086 if (p3 == null || p3.getPeriod().getDay() != p2.getPeriod().getDay() 087 || p3.getPeriod().getIndex() < p2.getPeriod().getIndex()) 088 continue; 089 if (p1.getPeriod().equals(p3.getPeriod()) && ex1.getId() >= ex3.getId()) 090 continue; 091 if (p2.getPeriod().equals(p3.getPeriod()) && ex2.getId() >= ex3.getId()) 092 continue; 093 int m2d = 0; 094 for (ExamStudent h : ex3.getStudents()) 095 if (students.contains(h)) 096 m2d++; 097 if (m2d == 0) 098 continue; 099 csv.addLine(new CSVField[] { 100 new CSVField(ex1.getName()), 101 new CSVField(ex1.getStudents().size()), 102 new CSVField(p1.getPeriod().getIndex() + 1), 103 new CSVField(p1.getPeriod().getDayStr()), 104 new CSVField(p1.getPeriod().getTimeStr()), 105 new CSVField(ex2.getName()), 106 new CSVField(ex2.getStudents().size()), 107 new CSVField(p2.getPeriod().getIndex() + 1), 108 new CSVField(p2.getPeriod().getTimeStr()), 109 new CSVField(ex3.getName()), 110 new CSVField(ex3.getStudents().size()), 111 new CSVField(p3.getPeriod().getIndex() + 1), 112 new CSVField(p3.getPeriod().getTimeStr()), 113 new CSVField(m2d), 114 new CSVField(df.format(100.0 115 * m2d 116 / Math.min(Math.min(ex1.getStudents().size(), ex2.getStudents().size()), ex3 117 .getStudents().size()))) }); 118 } 119 } 120 } 121 return csv; 122 } 123}