source: trunk/Test/Cbc_ampl.cpp @ 260

Last change on this file since 260 was 260, checked in by forrest, 14 years ago

for quit keyword

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 12.7 KB
Line 
1/****************************************************************
2Copyright (C) 1997-2000 Lucent Technologies
3Modifications for Coin -  Copyright (C) 2006, International Business Machines Corporation and others.
4All Rights Reserved
5
6Permission to use, copy, modify, and distribute this software and
7its documentation for any purpose and without fee is hereby
8granted, provided that the above copyright notice appear in all
9copies and that both that the copyright notice and this
10permission notice and warranty disclaimer appear in supporting
11documentation, and that the name of Lucent or any of its entities
12not be used in advertising or publicity pertaining to
13distribution of the software without specific, written prior
14permission.
15
16LUCENT DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
17INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS.
18IN NO EVENT SHALL LUCENT OR ANY OF ITS ENTITIES BE LIABLE FOR ANY
19SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
20WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER
21IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
22ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF
23THIS SOFTWARE.
24****************************************************************/
25#ifdef CBC_AMPL
26#include "getstub.h"
27#include "Cbc_ampl.h"
28#include "unistd.h"
29#include <string>
30/* so decodePhrase and clpCheck can access */
31static ampl_info * saveInfo=NULL;
32// Set to 1 if algorithm found
33static char algFound[20]="";
34static char*
35checkPhrase(Option_Info *oi, keyword *kw, char *v)
36{
37  if (strlen(v))
38    printf("string %s\n",v);
39  // Say algorithm found
40  strcpy(algFound,kw->desc);;
41  return v;
42}
43static char*
44checkPhrase2(Option_Info *oi, keyword *kw, char *v)
45{
46  if (strlen(v))
47    printf("string %s\n",v);
48  // put out keyword
49  saveInfo->arguments=(char **) realloc(saveInfo->arguments,(saveInfo->numberArguments+1)*sizeof(char *));
50  saveInfo->arguments[saveInfo->numberArguments++]=strdup(kw->desc);
51  return v;
52}
53static fint
54decodePhrase(char * phrase,ftnlen length)
55{
56  char * blank = strchr(phrase,' ');
57  if (blank) {
58    /* split arguments */
59    *blank='\0';
60    saveInfo->arguments=(char **) realloc(saveInfo->arguments,(saveInfo->numberArguments+2)*sizeof(char *));
61    saveInfo->arguments[saveInfo->numberArguments++]=strdup(phrase);
62    *blank=' ';
63    phrase=blank+1; /* move on */
64    saveInfo->arguments[saveInfo->numberArguments++]=strdup(phrase);
65  } else {
66    saveInfo->arguments=(char **) realloc(saveInfo->arguments,(saveInfo->numberArguments+1)*sizeof(char *));
67    saveInfo->arguments[saveInfo->numberArguments++]=strdup(phrase);
68  }
69  return 0;
70}
71static char xxxxxx[20];
72#define VP (char*)
73 static keyword keywds[] = { /* must be sorted */
74        { "barrier",    checkPhrase,            (char *) xxxxxx ,"-barrier" },
75        { "dual",       checkPhrase,            (char *) xxxxxx , "-dualsimplex"},
76        { "help",       checkPhrase2,           (char *) xxxxxx , "-?"},
77        { "initial",    checkPhrase,            (char *) xxxxxx , "-initialsolve"},
78        { "max",        checkPhrase2,           (char *) xxxxxx , "-maximize"},
79        { "maximize",   checkPhrase2,           (char *) xxxxxx , "-maximize"},
80        { "primal",     checkPhrase,            (char *) xxxxxx , "-primalsimplex"},
81        { "quit",       checkPhrase2,           (char *) xxxxxx , "-quit"},
82        { "wantsol",    WS_val,         NULL, "write .sol file (without -AMPL)" }
83        };
84static Option_Info Oinfo = {"cbc", "Cbc 1.01", "cbc_options", keywds, nkeywds, 0, "",
85                                0,decodePhrase,0,0,0, 20060130 };
86// strdup used to avoid g++ compiler warning
87 static SufDecl
88suftab[] = {
89#if 0
90        { "current", 0, ASL_Sufkind_con | ASL_Sufkind_outonly },
91        { "current", 0, ASL_Sufkind_var | ASL_Sufkind_outonly },
92        { "direction", 0, ASL_Sufkind_var },
93        { "down", 0, ASL_Sufkind_con | ASL_Sufkind_outonly },
94        { "down", 0, ASL_Sufkind_var | ASL_Sufkind_outonly },
95        { "priority", 0, ASL_Sufkind_var },
96        { "ref", 0, ASL_Sufkind_var | ASL_Sufkind_real },
97        { "sos", 0, ASL_Sufkind_var },
98        { "sos", 0, ASL_Sufkind_con },
99        { "sosno", 0, ASL_Sufkind_var | ASL_Sufkind_real },
100        { "sosref", 0, ASL_Sufkind_var | ASL_Sufkind_real },
101#endif
102        { strdup("sstatus"), 0, ASL_Sufkind_var, 0 },
103        { strdup("sstatus"), 0, ASL_Sufkind_con, 0 }
104#if 0
105        { "unbdd", 0, ASL_Sufkind_var | ASL_Sufkind_outonly},
106        { "up", 0, ASL_Sufkind_con | ASL_Sufkind_outonly },
107        { "up", 0, ASL_Sufkind_var | ASL_Sufkind_outonly }
108#endif
109        };
110#include "float.h"
111#include "limits.h"
112static ASL *asl=NULL;
113static FILE *nl=NULL;
114
115static void
116stat_map(int *stat, int n, int *map, int mx, const char *what)
117{
118  int bad, i, i1=0, j, j1=0;
119  static char badfmt[] = "Coin driver: %s[%d] = %d\n";
120 
121  for(i = bad = 0; i < n; i++) {
122    if ((j = stat[i]) >= 0 && j <= mx)
123      stat[i] = map[j];
124    else {
125      stat[i] = 0;
126      i1 = i;
127      j1 = j;
128      if (!bad++)
129        fprintf(Stderr, badfmt, what, i, j);
130    }
131  }
132  if (bad > 1) {
133    if (bad == 2)
134      fprintf(Stderr, badfmt, what, i1, j1);
135    else
136      fprintf(Stderr,
137              "Coin driver: %d messages about bad %s values suppressed.\n",
138              bad-1, what);
139  }
140}
141int
142readAmpl(ampl_info * info, int argc, char **argv)
143{
144  char *stub;
145  ograd *og;
146  int i;
147  SufDesc *csd;
148  SufDesc *rsd;
149  /*bool *basis, *lower;*/
150  /*double *LU, *c, lb, objadj, *rshift, *shift, t, ub, *x, *x0, *x1;*/
151  char * environment = getenv("cbc_options");
152  char tempBuffer[20];
153  double * obj;
154  double * columnLower;
155  double * columnUpper;
156  double * rowLower;
157  double * rowUpper;
158  char ** saveArgv=argv;
159  int saveArgc = argc;
160  memset(info,0,sizeof(ampl_info));
161  /* save so can be accessed by decodePhrase */
162  saveInfo = info;
163  info->numberArguments=0;
164  info->arguments=(char **) malloc(2*sizeof(char *));
165  info->arguments[info->numberArguments++]=strdup("ampl");
166  info->arguments[info->numberArguments++]=strdup("cbc");
167  asl = ASL_alloc(ASL_read_f);
168  stub = getstub(&argv, &Oinfo);
169  if (!stub)
170    usage_ASL(&Oinfo, 1);
171  nl = jac0dim(stub, 0);
172  /*void * specialOrderedInfo = sos_add(nl,0);*/
173  suf_declare(suftab, sizeof(suftab)/sizeof(SufDecl));
174 
175  /* set A_vals to get the constraints column-wise (malloc so can be freed) */
176  A_vals = (double *) malloc(nzc*sizeof(double));
177  if (!A_vals) {
178    printf("no memory\n");
179    return 1;
180  }
181  /* say we want primal solution */
182  want_xpi0=1;
183  /* for basis info */
184  info->columnStatus = (int *) malloc(n_var*sizeof(int));
185  info->rowStatus = (int *) malloc(n_con*sizeof(int));
186  csd = suf_iput("sstatus", ASL_Sufkind_var, info->columnStatus);
187  rsd = suf_iput("sstatus", ASL_Sufkind_con, info->rowStatus);
188  /* read linear model*/
189  f_read(nl,0);
190
191  /*sos_finish(&specialOrderedInfo, 0, &j, 0, 0, 0, 0, 0);*/
192  Oinfo.uinfo = tempBuffer;
193  if (getopts(argv, &Oinfo))
194    return 1;
195  /* objective*/
196  obj = (double *) malloc(n_var*sizeof(double));
197  for (i=0;i<n_var;i++)
198    obj[i]=0.0;;
199  if (n_obj) {
200    for (og = Ograd[0];og;og = og->next)
201      obj[og->varno] = og->coef;
202  }
203  if (objtype[0])
204    info->direction=-1.0;
205  else
206    info->direction=1.0;
207  info->offset=objconst(0);
208  /* Column bounds*/
209  columnLower = (double *) malloc(n_var*sizeof(double));
210  columnUpper = (double *) malloc(n_var*sizeof(double));
211#define COIN_DBL_MAX DBL_MAX
212  for (i=0;i<n_var;i++) {
213    columnLower[i]=LUv[2*i];
214    if (columnLower[i]<= negInfinity)
215      columnLower[i]=-COIN_DBL_MAX;
216    columnUpper[i]=LUv[2*i+1];
217    if (columnUpper[i]>= Infinity)
218      columnUpper[i]=COIN_DBL_MAX;
219  }
220  /* Row bounds*/
221  rowLower = (double *) malloc(n_con*sizeof(double));
222  rowUpper = (double *) malloc(n_con*sizeof(double));
223  for (i=0;i<n_con;i++) {
224    rowLower[i]=LUrhs[2*i];
225    if (rowLower[i]<= negInfinity)
226      rowLower[i]=-COIN_DBL_MAX;
227    rowUpper[i]=LUrhs[2*i+1];
228    if (rowUpper[i]>= Infinity)
229      rowUpper[i]=COIN_DBL_MAX;
230  }
231  info->numberRows=n_con;
232  info->numberColumns=n_var;
233  info->numberElements=nzc;;
234  info->numberBinary=nbv;
235  info->numberIntegers=niv;
236  info->objective=obj;
237  info->rowLower=rowLower;
238  info->rowUpper=rowUpper;
239  info->columnLower=columnLower;
240  info->columnUpper=columnUpper;
241  info->starts=A_colstarts;
242  /*A_colstarts=NULL;*/
243  info->rows=A_rownos;
244  /*A_rownos=NULL;*/
245  info->elements=A_vals;
246  /*A_vals=NULL;*/
247  info->primalSolution=NULL;
248  /* put in primalSolution if exists */
249  if (X0) {
250    info->primalSolution=(double *) malloc(n_var*sizeof(double));
251    memcpy(info->primalSolution,X0,n_var*sizeof(double));
252  }
253  info->dualSolution=NULL;
254  if ((!(niv+nbv)&&(csd->kind & ASL_Sufkind_input))
255      ||(rsd->kind & ASL_Sufkind_input)) {
256    /* convert status - need info on map */
257    static int map[] = {1, 3, 1, 1, 2, 1, 1};
258    stat_map(info->columnStatus, n_var, map, 6, "incoming columnStatus");
259    stat_map(info->rowStatus, n_con, map, 6, "incoming rowStatus");
260  } else {
261    /* all slack basis */
262    free(info->rowStatus);
263    info->rowStatus=NULL;
264    free(info->columnStatus);
265    info->columnStatus=NULL;
266  }
267  /* add -solve - unless something there already
268   - also check for sleep=yes */
269  {
270    int found=0;
271    int foundLog=0;
272    int foundSleep=0;
273    const char * something[]={"solve","branch","duals","primals"};
274    for (i=0;i<info->numberArguments;i++) {
275      unsigned int j;
276      const char * argument = info->arguments[i];
277      for (j=0;j<sizeof(something)/sizeof(char *);j++) {
278        const char * check = something[j];
279        if (!strncmp(argument,check,sizeof(check))) {
280          found=(int)(j+1);
281        } else if (!strncmp(argument,"log",3)) {
282          foundLog=1;
283        } else if (!strncmp(argument,"sleep",5)) {
284          foundSleep=1;
285        }
286      }
287    }
288    if (foundLog) {
289      /* print options etc */
290      for (i=0;i<saveArgc;i++)
291        printf("%s ",saveArgv[i]);
292      printf("\n");
293      if (environment)
294        printf("env %s\n",environment);
295      /*printf("%d rows %d columns %d elements\n",n_con,n_var,nzc);*/
296    }
297    if (!found) {
298      if (!strlen(algFound)) {
299        info->arguments=(char **) realloc(info->arguments,(info->numberArguments+1)*sizeof(char *));
300        info->arguments[info->numberArguments++]=strdup("-solve");
301      } else {
302        // use algorithm from keyword
303        info->arguments=(char **) realloc(info->arguments,(info->numberArguments+1)*sizeof(char *));
304        info->arguments[info->numberArguments++]=strdup(algFound);
305      }
306    }
307    if (foundSleep) {
308      /* let user copy .nl file */
309      fprintf(stderr,"You can copy .nl file %s for debug purposes or attach debugger\n",saveArgv[1]);
310      fprintf(stderr,"Type q to quit, anything else to continue\n");
311      char getChar = getc(stdin);
312      if (getChar=='q'||getChar=='Q')
313        exit(1);
314    }
315  }
316  /* add -quit */
317  info->arguments=(char **) realloc(info->arguments,(info->numberArguments+1)*sizeof(char *));
318  info->arguments[info->numberArguments++]=strdup("-quit");
319  return 0;
320}
321void freeArrays1(ampl_info * info)
322{
323  free(info->objective);
324  info->objective=NULL;
325  free(info->rowLower);
326  info->rowLower=NULL;
327  free(info->rowUpper);
328  info->rowUpper=NULL;
329  free(info->columnLower);
330  info->columnLower=NULL;
331  free(info->columnUpper);
332  info->columnUpper=NULL;
333  /* this one not freed by ASL_free */
334  free(info->elements);
335  info->elements=NULL;
336  free(info->primalSolution);
337  info->primalSolution=NULL;
338  free(info->dualSolution);
339  info->dualSolution=NULL;
340  /*free(info->rowStatus);
341  info->rowStatus=NULL;
342  free(info->columnStatus);
343  info->columnStatus=NULL;*/
344}
345void freeArrays2(ampl_info * info)
346{
347  free(info->primalSolution);
348  info->primalSolution=NULL;
349  free(info->dualSolution);
350  info->dualSolution=NULL;
351  free(info->rowStatus);
352  info->rowStatus=NULL;
353  free(info->columnStatus);
354  info->columnStatus=NULL;
355  ASL_free(&asl);
356}
357void freeArgs(ampl_info * info)
358{
359  int i;
360  for ( i=0; i<info->numberArguments;i++)
361    free(info->arguments[i]);
362  free(info->arguments);
363}
364int ampl_obj_prec()
365{
366  return obj_prec();
367}
368void writeAmpl(ampl_info * info)
369{
370  char buf[1000];
371  typedef struct { const char *msg; int code; int wantObj; } Sol_info;
372  static Sol_info solinfo[] = {
373    { "optimal solution",                       000, 1 },
374    { "infeasible",                             200, 1 },
375    { "unbounded",                              300, 0 },
376    { "iteration limit etc",                    400, 1 },
377    { "solution limit",                         401, 1 },
378    { "ran out of space",                       500, 0 },
379    { "status unknown",                         501, 1 },
380    { "bug!",                                   502, 0 },
381    { "best MIP solution so far restored",      101, 1 },
382    { "failed to restore best MIP solution",    503, 1 },
383    { "optimal (?) solution",                   100, 1 }
384  };
385  /* convert status - need info on map */
386  static int map[] = {0, 3, 4, 1};
387  sprintf(buf,"%s %s",Oinfo.bsname,info->buffer);
388  solve_result_num = solinfo[info->problemStatus].code;
389  if (info->columnStatus) {
390    stat_map(info->columnStatus, n_var, map, 4, "outgoing columnStatus");
391    stat_map(info->rowStatus, n_con, map, 4, "outgoing rowStatus");
392    suf_iput("sstatus", ASL_Sufkind_var, info->columnStatus);
393    suf_iput("sstatus", ASL_Sufkind_con, info->rowStatus);
394  }
395  write_sol(buf,info->primalSolution,info->dualSolution,&Oinfo);
396}
397
398#endif
Note: See TracBrowser for help on using the repository browser.