001package net.sf.cpsolver.ifs.example.tt;
002
003import java.util.HashSet;
004import java.util.Set;
005
006import net.sf.cpsolver.ifs.model.Constraint;
007import net.sf.cpsolver.ifs.model.Model;
008
009/**
010 * Resource constraint
011 * 
012 * @version IFS 1.2 (Iterative Forward Search)<br>
013 *          Copyright (C) 2006 - 2010 Tomáš Müller<br>
014 *          <a href="mailto:muller@unitime.org">muller@unitime.org</a><br>
015 *          <a href="http://muller.unitime.org">http://muller.unitime.org</a><br>
016 * <br>
017 *          This library is free software; you can redistribute it and/or modify
018 *          it under the terms of the GNU Lesser General Public License as
019 *          published by the Free Software Foundation; either version 3 of the
020 *          License, or (at your option) any later version. <br>
021 * <br>
022 *          This library is distributed in the hope that it will be useful, but
023 *          WITHOUT ANY WARRANTY; without even the implied warranty of
024 *          MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
025 *          Lesser General Public License for more details. <br>
026 * <br>
027 *          You should have received a copy of the GNU Lesser General Public
028 *          License along with this library; if not see
029 *          <a href='http://www.gnu.org/licenses/'>http://www.gnu.org/licenses/</a>.
030 */
031public class Resource extends Constraint<Activity, Location> {
032    private String iName = null;
033    private String iResourceId = null;
034    private Activity[] iResource;
035    private Set<Integer> iProhibitedSlots = new HashSet<Integer>();
036    private Set<Integer> iDiscouragedSlots = new HashSet<Integer>();
037    private int iType = TYPE_OTHER;
038    
039    public static final int TYPE_ROOM = 0;
040    public static final int TYPE_INSTRUCTOR = 1;
041    public static final int TYPE_CLASS = 2;
042    public static final int TYPE_OTHER = 3;
043
044    public Resource(String id, int type, String name) {
045        super();
046        iResourceId = id;
047        iName = name;
048        iType = type;
049    }
050    
051    @Override
052    public void setModel(Model<Activity, Location> model) {
053        super.setModel(model);
054        TimetableModel m = (TimetableModel)model;
055        iResource = new Activity[m.getNrDays() * m.getNrHours()];
056        for (int i=0;i<iResource.length;i++)
057                iResource[i] = null;
058    }
059    
060    public String getResourceId() { return iResourceId; }
061    @Override
062        public String getName() { return iName; }
063    public int getType() { return iType; }
064    public Set<Integer> getProhibitedSlots() { return iProhibitedSlots; }
065    public Set<Integer> getDiscouragedSlots() { return iDiscouragedSlots; }
066    public void addProhibitedSlot(int day, int hour) {
067        iProhibitedSlots.add(((TimetableModel)getModel()).getNrHours()*day+hour);
068    }
069    public void addDiscouragedSlot(int day, int hour) {
070        iDiscouragedSlots.add(((TimetableModel)getModel()).getNrHours()*day+hour);
071    }
072    public boolean isProhibitedSlot(int day, int hour) {
073        return iProhibitedSlots.contains(((TimetableModel)getModel()).getNrHours()*day+hour);
074    }
075    public boolean isDiscouragedSlot(int day, int hour) {
076        return iDiscouragedSlots.contains(((TimetableModel)getModel()).getNrHours()*day+hour);
077    }
078    public void addProhibitedSlot(int slot) {
079        iProhibitedSlots.add(slot);
080    }
081    public void addDiscouragedSlot(int slot) {
082        iDiscouragedSlots.add(slot);
083    }
084    public boolean isProhibitedSlot(int slot) {
085        return iProhibitedSlots.contains(slot);
086    }
087    public boolean isDiscouragedSlot(int slot) {
088        return iDiscouragedSlots.contains(slot);
089    }    
090    public boolean isProhibited(int day, int hour, int length) {
091        int slot = ((TimetableModel)getModel()).getNrHours()*day+hour;
092        for (int i=0;i<length;i++)
093            if (iProhibitedSlots.contains(slot+i)) return true;
094        return false;
095    }
096    
097    @Override
098        public void computeConflicts(Location location, Set<Location> conflicts) {
099        Activity activity = location.variable();
100        if (!location.containResource(this)) return;
101        for (int i=location.getSlot(); i<location.getSlot()+activity.getLength(); i++) {
102            Activity conf = iResource[i];
103            if (conf!=null && !activity.equals(conf)) 
104                conflicts.add(conf.getAssignment());
105        }
106    }
107    
108    @Override
109        public boolean inConflict(Location location) {
110        Activity activity = location.variable();
111        if (!location.containResource(this)) return false;
112        for (int i=location.getSlot(); i<location.getSlot()+activity.getLength(); i++) {
113            if (iResource[i]!=null) return true;
114        }
115        return false;
116    }
117        
118    @Override
119        public boolean isConsistent(Location l1, Location l2) {
120        return !l1.containResource(this) || !l2.containResource(this) || !l1.hasIntersection(l2);
121    }
122    
123    @Override
124        public void assigned(long iteration, Location location) {
125        super.assigned(iteration, location);
126        Activity activity = location.variable();
127        if (!location.containResource(this)) return;
128        for (int i=location.getSlot(); i<location.getSlot()+activity.getLength(); i++) {
129            iResource[i] = activity;
130        }
131    }
132    @Override
133        public void unassigned(long iteration, Location location) {
134        super.unassigned(iteration, location);
135        Activity activity = location.variable();
136        if (!location.containResource(this)) return;
137        for (int i=location.getSlot(); i<location.getSlot()+activity.getLength(); i++) {
138            iResource[i] = null;
139        }
140    }
141}