001 package net.sf.cpsolver.ifs.extension;
002
003 import net.sf.cpsolver.ifs.model.Constraint;
004 import net.sf.cpsolver.ifs.model.Value;
005
006 /**
007 * This class describing an assignment of a value to a variable together with a counter (used by CBS).
008 *
009 * Counter also supports ageing: the counter is multiplied by aging factor for each iteration.
010 *
011 * @version
012 * IFS 1.1 (Iterative Forward Search)<br>
013 * Copyright (C) 2006 Tomáš Müller<br>
014 * <a href="mailto:muller@unitime.org">muller@unitime.org</a><br>
015 * Lazenska 391, 76314 Zlin, Czech Republic<br>
016 * <br>
017 * This library is free software; you can redistribute it and/or
018 * modify it under the terms of the GNU Lesser General Public
019 * License as published by the Free Software Foundation; either
020 * version 2.1 of the License, or (at your option) any later version.
021 * <br><br>
022 * This library is distributed in the hope that it will be useful,
023 * but 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.
026 * <br><br>
027 * You should have received a copy of the GNU Lesser General Public
028 * License along with this library; if not, write to the Free Software
029 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
030 */
031 public class Assignment {
032 private Value iValue;
033 private double iCounter = 1.0;
034 private long iLastRevision;
035 private double iAgeing = 1.0;
036 private Constraint iConstraint = null;
037
038 /** Constructor
039 * @param iteration current iteration
040 * @param value value
041 * @param ageing ageing factor
042 */
043 public Assignment(long iteration, Value value, double ageing) {
044 iValue = value;
045 iLastRevision = iteration;
046 iAgeing = ageing;
047 }
048
049 /** Returns value */
050 public Value getValue() {
051 return iValue;
052 }
053
054 /** Increments counter
055 * @param iteration current iteration
056 */
057 public void incCounter(long iteration) {
058 revise(iteration);
059 iCounter += 1.0;
060 }
061
062 /** Set counter
063 * @param cnt new value
064 */
065 public void setCounter(double cnt) {
066 iCounter = cnt;
067 }
068
069 /** Get counter
070 * @param iteration current iteration
071 */
072 public double getCounter(long iteration) {
073 if (iteration == 0l)
074 return iCounter;
075 if (iAgeing == 1.0)
076 return iCounter;
077 return iCounter * Math.pow(iAgeing, iteration - iLastRevision);
078 }
079
080 /** Returns constraint */
081 public Constraint getConstraint() {
082 return iConstraint;
083 }
084 /** Sets constraint */
085 public void setConstraint(Constraint constraint) {
086 iConstraint = constraint;
087 }
088
089 /** Revise counter. If ageing is used, counter is adopted to the current iteration: it is multiplited by ageing factor powered by the number of iterations since last revision.
090 */
091 public synchronized void revise(long iteration) {
092 if (iAgeing == 1.0)
093 return;
094 iCounter *= Math.pow(iAgeing, iteration - iLastRevision);
095 iLastRevision = iteration;
096 }
097
098 /** Combine two integers (for hash code)
099 */
100 public static int combine(int a, int b) {
101 int ret = 0;
102 for (int i = 0; i < 15; i++)
103 ret = ret | ((a & (1 << i)) << i) | ((b & (1 << i)) << (i + 1));
104 return ret;
105 }
106
107 public int hashCode() {
108 return iValue.hashCode();
109 }
110
111 public boolean equals(Object o) {
112 if (o==null || !(o instanceof Assignment)) return false;
113 return ((Assignment)o).getValue().equals(getValue());
114 }
115
116 /** Returns comparator of assignments */
117 public static java.util.Comparator getComparator(long iteration) {
118 return new AssignmentComparator(iteration);
119 }
120
121 /** String representation */
122 public String toString() {
123 return toString(0l, true);
124 }
125
126 /** String representation (e.g., 10x A := a)*/
127 public String toString(long iteration, boolean assignment) {
128 return (assignment ? getCounter(iteration) + "x " : "")
129 + getValue().variable().getName()
130 + (assignment ? " := " : " != ")
131 + getValue().getName();
132 }
133
134 /** Compare two assignments (their counters) */
135 public int compareTo(long iteration, Assignment a) {
136 int cmp =
137 getValue().variable().getName().compareTo(
138 a.getValue().variable().getName());
139 if (cmp != 0)
140 return cmp;
141 if (getCounter(iteration) != a.getCounter(iteration))
142 return (getCounter(iteration) < a.getCounter(iteration) ? 1 : -1);
143 return getValue().getName().compareTo(a.getValue().getName());
144 }
145
146 /** Assignment comparator */
147 public static class AssignmentComparator implements java.util.Comparator {
148 private long iIteration;
149 public AssignmentComparator(long iteration) {
150 iIteration = iteration;
151 }
152 public int compare(Object o1, Object o2) {
153 if (o1 == null
154 || o2 == null
155 || !(o1 instanceof Assignment)
156 || !(o2 instanceof Assignment))
157 return 0;
158 return ((Assignment)o1).compareTo(iIteration, (Assignment)o2);
159 }
160 }
161 }