00001
00002
00003
00004
00005
00006
00007
00008
00009 #include <polylib/polylib.h>
00010 #include <stdio.h>
00011 #include <stdlib.h>
00012 #include <string.h>
00013
00014 #ifdef dbg
00015 #undef dbg
00016 #endif
00017 #define dbg 1
00018
00019 #define TEST(a) if (isOk = a) { \
00020 printf(#a" tested ok.\n"); \
00021 } \
00022 else { \
00023 printf(#a" NOT OK\n"); \
00024 }
00025
00026 #define maxRays 200
00027
00028 const char *origNames[] =
00029 {"n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z"};
00030
00031 int main(int argc, char ** argv) {
00032 int isOk = 0;
00033 Matrix * A, * B;
00034 if (argc>1) {
00035 printf("Warning: No arguments taken into account: testing"
00036 "remove_parm_eqs().\n");
00037 }
00038
00039 A = Matrix_Read();
00040 B = Matrix_Read();
00041 TEST( test_Constraints_Remove_parm_eqs(A, B) )
00042 TEST( test_Polyhedron_Remove_parm_eqs(A, B) )
00043 TEST( test_Constraints_fullDimensionize(A, B, 4) )
00044 Matrix_Free(A);
00045 Matrix_Free(B);
00046 return (1-isOk);
00047 }
00048
00049
00050
00051
00052
00053
00054 int test_Constraints_Remove_parm_eqs(Matrix * A, Matrix * B) {
00055 int isOk = 1;
00056 Matrix * M, *C, *Cp, * Eqs, *M1, *C1;
00057 Polyhedron *Pm, *Pc, *Pcp, *Peqs, *Pint;
00058 unsigned int * elimParms;
00059 printf("----- test_Constraints_Remove_parm_eqs() -----\n");
00060 M1 = Matrix_Copy(A);
00061 C1 = Matrix_Copy(B);
00062
00063 M = Matrix_Copy(M1);
00064 C = Matrix_Copy(C1);
00065
00066
00067 Pm = Constraints2Polyhedron(M, maxRays);
00068 Pc = Constraints2Polyhedron(C, maxRays);
00069 Pcp = align_context(Pc, Pm->Dimension, maxRays);
00070 Polyhedron_Free(Pc);
00071 Pc = DomainIntersection(Pm, Pcp, maxRays);
00072 Polyhedron_Free(Pm);
00073 Polyhedron_Free(Pcp);
00074 Matrix_Free(M);
00075 Matrix_Free(C);
00076
00077
00078 Eqs = Constraints_Remove_parm_eqs(&M1, &C1, 1, &elimParms);
00079
00080 printf("Removed equalities: \n");
00081 show_matrix(Eqs);
00082 printf("Polyhedron without equalities involving only parameters: \n");
00083 show_matrix(M1);
00084 printf("Context without equalities: \n");
00085 show_matrix(C1);
00086
00087
00088 Pm = Constraints2Polyhedron(M1, maxRays);
00089 Pcp = Constraints2Polyhedron(C1, maxRays);
00090 Peqs = align_context(Pcp, Pm->Dimension, maxRays);
00091 Polyhedron_Free(Pcp);
00092 Pcp = DomainIntersection(Pm, Peqs, maxRays);
00093 Polyhedron_Free(Peqs);
00094 Polyhedron_Free(Pm);
00095 Peqs = Constraints2Polyhedron(Eqs, maxRays);
00096 Matrix_Free(Eqs);
00097 Matrix_Free(M1);
00098 Matrix_Free(C1);
00099 Pint = DomainIntersection(Pcp, Peqs, maxRays);
00100 Polyhedron_Free(Pcp);
00101 Polyhedron_Free(Peqs);
00102
00103
00104 if (!PolyhedronIncludes(Pint, Pc)) {
00105 isOk = 0;
00106 }
00107 else {
00108 if (!PolyhedronIncludes(Pc, Pint)) {
00109 isOk = 0;
00110 }
00111 }
00112 Polyhedron_Free(Pc);
00113 Polyhedron_Free(Pint);
00114 return isOk;
00115 }
00116
00117
00118
00119
00120
00121
00122 int test_Polyhedron_Remove_parm_eqs(Matrix * A, Matrix * B) {
00123 int isOk = 1;
00124 Matrix * M, *C;
00125 Polyhedron *Pm, *Pc, *Pcp, *Peqs, *Pint, *Pint1;
00126 unsigned int * elimParms;
00127 printf("----- test_Polyhedron_Remove_parm_eqs() -----\n");
00128
00129 M = Matrix_Copy(A);
00130 C = Matrix_Copy(B);
00131
00132
00133 Pm = Constraints2Polyhedron(M, maxRays);
00134 Pc = Constraints2Polyhedron(C, maxRays);
00135 Pcp = align_context(Pc, Pm->Dimension, maxRays);
00136 Polyhedron_Free(Pc);
00137 Pint1 = DomainIntersection(Pm, Pcp, maxRays);
00138 Polyhedron_Free(Pm);
00139 Polyhedron_Free(Pcp);
00140 Matrix_Free(M);
00141 Matrix_Free(C);
00142
00143 M = Matrix_Copy(A);
00144 C = Matrix_Copy(B);
00145
00146 Pm = Constraints2Polyhedron(M, maxRays);
00147 Pc = Constraints2Polyhedron(C, maxRays);
00148 Matrix_Free(M);
00149 Matrix_Free(C);
00150 Peqs = Polyhedron_Remove_parm_eqs(&Pm, &Pc, 1, &elimParms, 200);
00151
00152
00153 Pcp = align_context(Pc, Pm->Dimension, maxRays);
00154 Polyhedron_Free(Pc);
00155 Pc = DomainIntersection(Pm, Pcp, maxRays);
00156 Polyhedron_Free(Pm);
00157 Polyhedron_Free(Pcp);
00158
00159 Pint = DomainIntersection(Pc, Peqs, maxRays);
00160 Polyhedron_Free(Pc);
00161 Polyhedron_Free(Peqs);
00162
00163
00164 if (!PolyhedronIncludes(Pint, Pint1)) {
00165 isOk = 0;
00166 }
00167 else {
00168 if (!PolyhedronIncludes(Pint1, Pint)) {
00169 isOk = 0;
00170 }
00171 }
00172 Polyhedron_Free(Pint1);
00173 Polyhedron_Free(Pint);
00174 return isOk;
00175 }
00176
00177
00178
00179
00180
00181
00182
00183
00184 void valuesWithoutElim(Matrix * origParms, unsigned int * elimParms,
00185 Matrix ** newParms) {
00186 unsigned int i, j=0;
00187 if (*newParms==NULL) {
00188 *newParms = Matrix_Alloc(1, origParms->NbColumns-elimParms[0]);
00189 }
00190 if (elimParms[0] ==0) {
00191 for (i=0; i< origParms->NbColumns; i++) {
00192 value_assign((*newParms)->p[0][i], origParms->p[0][i]);
00193 }
00194 }
00195 for (i=0; i< origParms->NbColumns; i++) {
00196 if (i!=elimParms[j+1]) {
00197 value_assign((*newParms)->p[0][i-j], origParms->p[0][i]);
00198 }
00199 else {
00200 j++;
00201 }
00202 }
00203 }
00204
00205
00206
00207
00208
00209
00210
00211
00212
00213
00214
00215
00216
00217 unsigned int namesWithoutElim(const char **parms, unsigned nbParms,
00218 unsigned int * elimParms,
00219 const char ***newParms)
00220 {
00221 unsigned int i, j=0;
00222 unsigned int newSize = nbParms -elimParms[0];
00223 if (dbg) {
00224 printf("Size of the new parm vector: %d\n", newSize);
00225 }
00226 if (*newParms==NULL) {
00227 *newParms = malloc(newSize*sizeof(char *));
00228 }
00229 if (elimParms[0]==0) {
00230 for (i=0; i< nbParms; i++) {
00231 (*newParms)[i] = strdup(parms[i]);
00232 }
00233 return newSize;
00234 }
00235 for (i=0; i< nbParms; i++) {
00236 if (i!=elimParms[j+1]) {
00237 (*newParms)[i-j] = strdup(parms[i]);
00238 }
00239 else {
00240 j++;
00241 }
00242 }
00243 return newSize;
00244 }
00245
00246
00247
00248
00249
00250
00251
00252
00253
00254
00255
00256 int test_Constraints_fullDimensionize(Matrix * A, Matrix * B,
00257 unsigned int nbSamples) {
00258 Matrix * Eqs= NULL, *ParmEqs=NULL, *VL=NULL;
00259 unsigned int * elimVars=NULL, * elimParms=NULL;
00260 Matrix * sample, * smallerSample=NULL;
00261 Matrix * transfSample=NULL;
00262 Matrix * parmVL=NULL;
00263 unsigned int i, j, r, nbOrigParms, nbParms;
00264 Value div, mod, *origVal=NULL, *fullVal=NULL;
00265 Matrix * VLInv;
00266 Polyhedron * P, *PC;
00267 Matrix * M, *C;
00268 Enumeration * origEP, * fullEP=NULL;
00269 const char **fullNames = NULL;
00270 int isOk = 1;
00271
00272
00273 M = Matrix_Copy(A);
00274 C = Matrix_Copy(B);
00275 P = Constraints2Polyhedron(M, maxRays);
00276 PC = Constraints2Polyhedron(C, maxRays);
00277 origEP = Polyhedron_Enumerate(P, PC, maxRays, origNames);
00278 Matrix_Free(M);
00279 Matrix_Free(C);
00280 Polyhedron_Free(P);
00281 Polyhedron_Free(PC);
00282
00283
00284
00285 M = Matrix_Copy(A);
00286 C = Matrix_Copy(B);
00287 nbOrigParms = B->NbColumns-2;
00288 Constraints_fullDimensionize(&M, &C, &VL, &Eqs, &ParmEqs,
00289 &elimVars, &elimParms, maxRays);
00290 if ((Eqs->NbRows==0) && (ParmEqs->NbRows==0)) {
00291 Matrix_Free(M);
00292 Matrix_Free(C);
00293 Matrix_Free(Eqs);
00294 Matrix_Free(ParmEqs);
00295 free(elimVars);
00296 free(elimParms);
00297 return 1;
00298 }
00299 nbParms = C->NbColumns-2;
00300 P = Constraints2Polyhedron(M, maxRays);
00301 PC = Constraints2Polyhedron(C, maxRays);
00302 namesWithoutElim(origNames, nbOrigParms, elimParms, &fullNames);
00303 fullEP = Polyhedron_Enumerate(P, PC, maxRays, fullNames);
00304 Matrix_Free(M);
00305 Matrix_Free(C);
00306 Polyhedron_Free(P);
00307 Polyhedron_Free(PC);
00308
00309
00310
00311 sample = Matrix_Alloc(1,nbOrigParms);
00312 transfSample = Matrix_Alloc(1, nbParms);
00313 Lattice_extractSubLattice(VL, nbParms, &parmVL);
00314 VLInv = Matrix_Alloc(parmVL->NbRows, parmVL->NbRows+1);
00315 MatInverse(parmVL, VLInv);
00316 if (dbg) {
00317 show_matrix(parmVL);
00318 show_matrix(VLInv);
00319 }
00320 srand(nbSamples);
00321 value_init(mod);
00322 value_init(div);
00323 for (i = 0; i< nbSamples; i++) {
00324
00325 for (j=0; j< nbOrigParms; j++) {
00326 value_set_si(sample->p[0][j], rand()%100);
00327 }
00328
00329
00330 valuesWithoutElim(sample, elimParms, &smallerSample);
00331
00332 for (r = 0; r < nbParms; r++) {
00333 Inner_Product(&(VLInv->p[r][0]), smallerSample->p[0], nbParms,
00334 &(transfSample->p[0][r]));
00335
00336 value_addto(transfSample->p[0][r], transfSample->p[0][r],
00337 VLInv->p[r][VLInv->NbColumns-2]);
00338 value_pdivision(div, transfSample->p[0][r],
00339 VLInv->p[r][VLInv->NbColumns-1]);
00340 value_subtract(mod, transfSample->p[0][r], div);
00341
00342
00343 if (!value_zero_p(mod)) {
00344 fullEP = Enumeration_zero(nbParms, maxRays);
00345 break;
00346 }
00347 }
00348
00349 if (origEP ==NULL) break;
00350 origVal = compute_poly(origEP, sample->p[0]);
00351 fullVal = compute_poly(fullEP, transfSample->p[0]);
00352 if (!value_eq(*origVal, *fullVal)) {
00353 isOk = 0;
00354 printf("EPs don't match. \n Original value = ");
00355 value_print(stdout, VALUE_FMT, *origVal);
00356 printf("\n Original sample = [");
00357 for (j=0; j<sample->NbColumns; j++) {
00358 value_print(stdout, VALUE_FMT, sample->p[0][j]);
00359 printf(" ");
00360 }
00361 printf("] \n EP = ");
00362 if(origEP!=NULL) {
00363 print_evalue(stdout, &(origEP->EP), origNames);
00364 }
00365 else {
00366 printf("NULL");
00367 }
00368 printf(" \n Full-dimensional value = ");
00369 value_print(stdout, P_VALUE_FMT, *fullVal);
00370 printf("\n full-dimensional sample = [");
00371 for (j=0; j<sample->NbColumns; j++) {
00372 value_print(stdout, VALUE_FMT, transfSample->p[0][j]);
00373 printf(" ");
00374 }
00375 printf("] \n EP = ");
00376 if(origEP!=NULL) {
00377 print_evalue(stdout, &(origEP->EP), fullNames);
00378 }
00379 else {
00380 printf("NULL");
00381 }
00382 }
00383 if (dbg) {
00384 printf("\nOriginal value = ");
00385 value_print(stdout, VALUE_FMT, *origVal);
00386 printf("\nFull-dimensional value = ");
00387 value_print(stdout, P_VALUE_FMT, *fullVal);
00388 printf("\n");
00389 }
00390 value_clear(*origVal);
00391 value_clear(*fullVal);
00392 }
00393 value_clear(mod);
00394 value_clear(div);
00395 Matrix_Free(sample);
00396 Matrix_Free(smallerSample);
00397 Matrix_Free(transfSample);
00398 Enumeration_Free(origEP);
00399 Enumeration_Free(fullEP);
00400 return isOk;
00401 }