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
00037
00038 #include "gecode/int/rel.hh"
00039 #include "gecode/int/bool.hh"
00040
00046 namespace Gecode {
00047
00048 namespace Int { namespace Unshare {
00049
00051 template<class Var>
00052 class VarPtrLess {
00053 public:
00054 forceinline bool
00055 operator()(const Var* a, const Var* b) {
00056 return before(*a,*b);
00057 }
00058 };
00059
00060
00062 forceinline ExecStatus
00063 link(Space* home, IntVar** x, int n, IntConLevel icl) {
00064 if (n > 2) {
00065 ViewArray<IntView> y(home,n);
00066 y[0]=*x[0];
00067 for (int i=1; i<n; i++) {
00068 x[i]->init(home,x[0]->min(),x[0]->max()); y[i]=*x[i];
00069 }
00070 if ((icl == ICL_DOM) || (icl == ICL_DEF)) {
00071 GECODE_ES_CHECK(Rel::NaryEqDom<IntView>::post(home,y));
00072 } else {
00073 GECODE_ES_CHECK(Rel::NaryEqBnd<IntView>::post(home,y));
00074 }
00075 } else if (n == 2) {
00076 IntVar z(home,x[0]->min(),x[0]->max());
00077 *x[1]=z;
00078 if ((icl == ICL_DOM) || (icl == ICL_DEF)) {
00079 GECODE_ES_CHECK((Rel::EqDom<IntView,IntView>::post
00080 (home,*x[0],*x[1])));
00081 } else {
00082 GECODE_ES_CHECK((Rel::EqBnd<IntView,IntView>::post
00083 (home,*x[0],*x[1])));
00084 }
00085 }
00086 return ES_OK;
00087 }
00088
00090 forceinline ExecStatus
00091 link(Space* home, BoolVar** x, int n, IntConLevel) {
00092 if (n > 2) {
00093 ViewArray<BoolView> y(home,n);
00094 y[0]=*x[0];
00095 for (int i=1; i<n; i++) {
00096 x[i]->init(home,0,1); y[i]=*x[i];
00097 }
00098 GECODE_ES_CHECK(Bool::NaryEq<BoolView>::post(home,y));
00099 } else if (n == 2) {
00100 x[1]->init(home,0,1);
00101 GECODE_ES_CHECK((Bool::Eq<BoolView,BoolView>::post(home,*x[0],*x[1])));
00102 }
00103 return ES_OK;
00104 }
00105
00107 template <class Var>
00108 forceinline ExecStatus
00109 unshare(Space* home, VarArgArray<Var>& x, IntConLevel icl) {
00110 int n=x.size();
00111 if (n < 2)
00112 return ES_OK;
00113
00114 GECODE_AUTOARRAY(Var*,y,n);
00115 for (int i=n; i--; )
00116 y[i]=&x[i];
00117
00118 VarPtrLess<Var> vpl;
00119 Support::quicksort<Var*,VarPtrLess<Var> >(y,n,vpl);
00120
00121
00122 for (int i=0; i<n;) {
00123 int j=i++;
00124 while ((i<n) && same(*y[j],*y[i]))
00125 i++;
00126 if (!y[j]->assigned())
00127 link(home,&y[j],i-j,icl);
00128 }
00129 return ES_OK;
00130 }
00131
00132 }}
00133
00134 void
00135 unshare(Space* home, IntVarArgs& x, IntConLevel icl, PropKind) {
00136 if (home->failed()) return;
00137 GECODE_ES_FAIL(home,Int::Unshare::unshare<IntVar>(home,x,icl));
00138 }
00139
00140 void
00141 unshare(Space* home, BoolVarArgs& x, IntConLevel, PropKind) {
00142 if (home->failed()) return;
00143 GECODE_ES_FAIL(home,Int::Unshare::unshare<BoolVar>(home,x,ICL_DEF));
00144 }
00145
00146 }
00147
00148