00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036 #include <gecode/int/unary.hh>
00037 #include <gecode/int/distinct.hh>
00038
00039 #include <algorithm>
00040
00041 namespace Gecode {
00042
00043 void
00044 unary(Home home, const IntVarArgs& s, const IntArgs& p, IntPropLevel ipl) {
00045 using namespace Gecode::Int;
00046 using namespace Gecode::Int::Unary;
00047 if (s.same())
00048 throw Int::ArgumentSame("Int::unary");
00049 if (s.size() != p.size())
00050 throw Int::ArgumentSizeMismatch("Int::unary");
00051 for (int i=p.size(); i--; ) {
00052 Int::Limits::nonnegative(p[i],"Int::unary");
00053 Int::Limits::check(static_cast<long long int>(s[i].max()) + p[i],
00054 "Int::unary");
00055 }
00056 GECODE_POST;
00057 bool allOne = true;
00058 for (int i=p.size(); i--;) {
00059 if (p[i] != 1) {
00060 allOne = false;
00061 break;
00062 }
00063 }
00064 if (allOne) {
00065 ViewArray<IntView> xv(home,s);
00066 switch (vbd(ipl)) {
00067 case IPL_BND:
00068 GECODE_ES_FAIL(Distinct::Bnd<IntView>::post(home,xv));
00069 break;
00070 case IPL_DOM:
00071 GECODE_ES_FAIL(Distinct::Dom<IntView>::post(home,xv));
00072 break;
00073 default:
00074 GECODE_ES_FAIL(Distinct::Val<IntView>::post(home,xv));
00075 }
00076 } else {
00077 TaskArray<ManFixPTask> t(home,s.size());
00078 for (int i=s.size(); i--; )
00079 t[i].init(s[i],p[i]);
00080 GECODE_ES_FAIL(manpost(home,t,ipl));
00081 }
00082 }
00083
00084 void
00085 unary(Home home, const TaskTypeArgs& t,
00086 const IntVarArgs& flex, const IntArgs& fix, IntPropLevel ipl) {
00087 using namespace Gecode::Int;
00088 using namespace Gecode::Int::Unary;
00089 if ((flex.size() != fix.size()) || (flex.size() != t.size()))
00090 throw Int::ArgumentSizeMismatch("Int::unary");
00091 for (int i=fix.size(); i--; ) {
00092 if (t[i] == TT_FIXP)
00093 Int::Limits::nonnegative(fix[i],"Int::unary");
00094 else
00095 Int::Limits::check(fix[i],"Int::unary");
00096 Int::Limits::check(static_cast<long long int>(flex[i].max()) + fix[i],
00097 "Int::unary");
00098 }
00099 GECODE_POST;
00100 bool fixp = true;
00101 for (int i=t.size(); i--;)
00102 if (t[i] != TT_FIXP) {
00103 fixp = false; break;
00104 }
00105 if (fixp) {
00106 unary(home, flex, fix, ipl);
00107 } else {
00108 TaskArray<ManFixPSETask> tasks(home,flex.size());
00109 for (int i=flex.size(); i--;)
00110 tasks[i].init(t[i],flex[i],fix[i]);
00111 GECODE_ES_FAIL(manpost(home,tasks,ipl));
00112 }
00113 }
00114
00115 void
00116 unary(Home home, const IntVarArgs& s, const IntArgs& p,
00117 const BoolVarArgs& m, IntPropLevel ipl) {
00118 using namespace Gecode::Int;
00119 using namespace Gecode::Int::Unary;
00120 if (s.same())
00121 throw Int::ArgumentSame("Int::unary");
00122 if ((s.size() != p.size()) || (s.size() != m.size()))
00123 throw Int::ArgumentSizeMismatch("Int::unary");
00124 for (int i=p.size(); i--; ) {
00125 Int::Limits::nonnegative(p[i],"Int::unary");
00126 Int::Limits::check(static_cast<long long int>(s[i].max()) + p[i],
00127 "Int::unary");
00128 }
00129 bool allMandatory = true;
00130 for (int i=m.size(); i--;) {
00131 if (!m[i].one()) {
00132 allMandatory = false;
00133 break;
00134 }
00135 }
00136 if (allMandatory) {
00137 unary(home,s,p,ipl);
00138 } else {
00139 GECODE_POST;
00140 TaskArray<OptFixPTask> t(home,s.size());
00141 for (int i=s.size(); i--; )
00142 t[i].init(s[i],p[i],m[i]);
00143 GECODE_ES_FAIL(optpost(home,t,ipl));
00144 }
00145 }
00146
00147 void
00148 unary(Home home, const TaskTypeArgs& t,
00149 const IntVarArgs& flex, const IntArgs& fix, const BoolVarArgs& m,
00150 IntPropLevel ipl) {
00151 using namespace Gecode::Int;
00152 using namespace Gecode::Int::Unary;
00153 if ((flex.size() != fix.size()) || (flex.size() != t.size()) ||
00154 (flex.size() != m.size()))
00155 throw Int::ArgumentSizeMismatch("Int::unary");
00156 bool fixp = true;
00157 for (int i=fix.size(); i--; ) {
00158 if (t[i] == TT_FIXP) {
00159 Int::Limits::nonnegative(fix[i],"Int::unary");
00160 } else {
00161 fixp = false;
00162 Int::Limits::check(fix[i],"Int::unary");
00163 }
00164 Int::Limits::check(static_cast<long long int>(flex[i].max()) + fix[i],
00165 "Int::unary");
00166 }
00167 GECODE_POST;
00168 bool allMandatory = true;
00169 for (int i=m.size(); i--;) {
00170 if (!m[i].one()) {
00171 allMandatory = false;
00172 break;
00173 }
00174 }
00175 if (allMandatory) {
00176 unary(home,t,flex,fix,ipl);
00177 } else {
00178 if (fixp) {
00179 TaskArray<OptFixPTask> tasks(home,flex.size());
00180 for (int i=flex.size(); i--; )
00181 tasks[i].init(flex[i],fix[i],m[i]);
00182 GECODE_ES_FAIL(optpost(home,tasks,ipl));
00183 } else {
00184 TaskArray<OptFixPSETask> tasks(home,flex.size());
00185 for (int i=flex.size(); i--;)
00186 tasks[i].init(t[i],flex[i],fix[i],m[i]);
00187 GECODE_ES_FAIL(optpost(home,tasks,ipl));
00188 }
00189 }
00190 }
00191
00192 void
00193 unary(Home home, const IntVarArgs& s, const IntVarArgs& p,
00194 const IntVarArgs& e, IntPropLevel ipl) {
00195 using namespace Gecode::Int;
00196 using namespace Gecode::Int::Unary;
00197 if ((s.size() != p.size()) || (s.size() != e.size()))
00198 throw Int::ArgumentSizeMismatch("Int::unary");
00199 GECODE_POST;
00200 for (int i=p.size(); i--; ) {
00201 rel(home, p[i], IRT_GQ, 0);
00202 }
00203 bool fixP = true;
00204 for (int i=p.size(); i--;) {
00205 if (!p[i].assigned()) {
00206 fixP = false;
00207 break;
00208 }
00209 }
00210 if (fixP) {
00211 IntArgs pp(p.size());
00212 for (int i=p.size(); i--;)
00213 pp[i] = p[i].val();
00214 unary(home,s,pp,ipl);
00215 } else {
00216 TaskArray<ManFlexTask> t(home,s.size());
00217 for (int i=s.size(); i--; )
00218 t[i].init(s[i],p[i],e[i]);
00219 GECODE_ES_FAIL(manpost(home,t,ipl));
00220 }
00221 }
00222
00223 void
00224 unary(Home home, const IntVarArgs& s, const IntVarArgs& p,
00225 const IntVarArgs& e, const BoolVarArgs& m, IntPropLevel ipl) {
00226 using namespace Gecode::Int;
00227 using namespace Gecode::Int::Unary;
00228 if ((s.size() != p.size()) || (s.size() != m.size()) ||
00229 (s.size() != e.size()))
00230 throw Int::ArgumentSizeMismatch("Int::unary");
00231 GECODE_POST;
00232 for (int i=p.size(); i--; ) {
00233 rel(home, p[i], IRT_GQ, 0);
00234 }
00235 bool allMandatory = true;
00236 for (int i=m.size(); i--;) {
00237 if (!m[i].one()) {
00238 allMandatory = false;
00239 break;
00240 }
00241 }
00242 if (allMandatory) {
00243 unary(home,s,p,e,ipl);
00244 } else {
00245 TaskArray<OptFlexTask> t(home,s.size());
00246 for (int i=s.size(); i--; )
00247 t[i].init(s[i],p[i],e[i],m[i]);
00248 GECODE_ES_FAIL(optpost(home,t,ipl));
00249 }
00250 }
00251
00252 }
00253
00254