struct type_nav *type_nav_init(void) { struct type_nav *root = umalloc(sizeof *root); root->btypes = ucalloc(type_unknown, sizeof *root->btypes); return root; }
si32 alloc_new_track(track_file_handle_t *t_handle, date_time_t *dtime, track_utime_t *track_utime, storm_status_t *storm, si32 scan_num, int new_complex_track, si32 complex_track_num, si32 history_in_scans, si32 scan_origin, date_time_t *time_origin) { si32 simple_track_num; simple_track_params_t *st_params; track_status_t *track; /* * set track number and increment ntracks, * checking for array space */ simple_track_num = t_handle->header->n_simple_tracks; t_handle->header->max_simple_track_num = simple_track_num; t_handle->header->n_simple_tracks++; if (RfAllocTrackSimpleArrays(t_handle, t_handle->header->n_simple_tracks, "alloc_new_track")) { tidy_and_exit(-1); } if (RfAllocSimplesPerComplex(t_handle, t_handle->header->n_simple_tracks, "alloc_new_track")) { tidy_and_exit(-1); } if (Glob->params.debug >= DEBUG_EXTRA) fprintf(stderr, "\nStarting simple track %ld\n", (long) simple_track_num); /* * initialize track_data struct */ storm->track = (track_status_t *) ucalloc ((ui32) 1, (ui32) sizeof(track_status_t)); track = storm->track; track->history = (storm_track_props_t *) ucalloc ((ui32) MAX_NWEIGHTS_FORECAST, (ui32) sizeof(storm_track_props_t)); track->simple_track_num = simple_track_num; track->duration_in_scans = 0; track->history_in_scans = history_in_scans; track->scan_origin = scan_origin; memcpy ((void *) &track->time_origin, (void *) time_origin, (size_t) sizeof(date_time_t)); /* * compute history in seconds */ track->history_in_secs = compute_history_in_secs(track, dtime, history_in_scans); /* * set up the track params */ st_params = t_handle->simple_params; memset ((void *) st_params, (int) 0, (size_t) sizeof(simple_track_params_t)); st_params->simple_track_num = simple_track_num; st_params->start_scan = scan_num; st_params->end_scan = scan_num; st_params->duration_in_scans = 0; st_params->duration_in_secs = 0; st_params->history_in_scans = history_in_scans; st_params->scan_origin = scan_origin; st_params->start_time = dtime->unix_time; st_params->end_time = dtime->unix_time; st_params->time_origin = time_origin->unix_time; track_utime[simple_track_num].start_simple = dtime->unix_time; track_utime[simple_track_num].end_simple = dtime->unix_time; if (new_complex_track) { track->complex_track_num = start_complex_track(t_handle, track, simple_track_num, track_utime); if (Glob->params.debug >= DEBUG_EXTRA) fprintf(stderr, "starting complex track %ld\n", (long) track->complex_track_num); } else { track->complex_track_num = augment_complex_track(t_handle, track, simple_track_num, complex_track_num); if (Glob->params.debug >= DEBUG_EXTRA) fprintf(stderr, "augmenting complex track %ld\n", (long) track->complex_track_num); } /* if (new_complex_track) */ st_params->complex_track_num = track->complex_track_num; /* * write simple track params to file */ if (RfWriteSimpleTrackParams(t_handle, simple_track_num, "alloc_new_track")) { tidy_and_exit(-1); } return (simple_track_num); }
LPX *lpx_extract_prob(void *_mpl) { MPL *mpl = _mpl; LPX *lp; int m, n, i, j, t, kind, type, len, *ind; double lb, ub, *val; /* create problem instance */ lp = lpx_create_prob(); /* set problem name */ lpx_set_prob_name(lp, mpl_get_prob_name(mpl)); /* build rows (constraints) */ m = mpl_get_num_rows(mpl); if (m > 0) lpx_add_rows(lp, m); for (i = 1; i <= m; i++) { /* set row name */ lpx_set_row_name(lp, i, mpl_get_row_name(mpl, i)); /* set row bounds */ type = mpl_get_row_bnds(mpl, i, &lb, &ub); switch (type) { case MPL_FR: type = LPX_FR; break; case MPL_LO: type = LPX_LO; break; case MPL_UP: type = LPX_UP; break; case MPL_DB: type = LPX_DB; break; case MPL_FX: type = LPX_FX; break; default: insist(type != type); } if (type == LPX_DB && fabs(lb - ub) < 1e-9 * (1.0 + fabs(lb))) { type = LPX_FX; if (fabs(lb) <= fabs(ub)) ub = lb; else lb = ub; } lpx_set_row_bnds(lp, i, type, lb, ub); /* warn about non-zero constant term */ if (mpl_get_row_c0(mpl, i) != 0.0) print("lpx_read_model: row %s; constant term %.12g ignored", mpl_get_row_name(mpl, i), mpl_get_row_c0(mpl, i)); } /* build columns (variables) */ n = mpl_get_num_cols(mpl); if (n > 0) lpx_add_cols(lp, n); for (j = 1; j <= n; j++) { /* set column name */ lpx_set_col_name(lp, j, mpl_get_col_name(mpl, j)); /* set column kind */ kind = mpl_get_col_kind(mpl, j); switch (kind) { case MPL_NUM: break; case MPL_INT: case MPL_BIN: lpx_set_class(lp, LPX_MIP); lpx_set_col_kind(lp, j, LPX_IV); break; default: insist(kind != kind); } /* set column bounds */ type = mpl_get_col_bnds(mpl, j, &lb, &ub); switch (type) { case MPL_FR: type = LPX_FR; break; case MPL_LO: type = LPX_LO; break; case MPL_UP: type = LPX_UP; break; case MPL_DB: type = LPX_DB; break; case MPL_FX: type = LPX_FX; break; default: insist(type != type); } if (kind == MPL_BIN) { if (type == LPX_FR || type == LPX_UP || lb < 0.0) lb = 0.0; if (type == LPX_FR || type == LPX_LO || ub > 1.0) ub = 1.0; type = LPX_DB; } if (type == LPX_DB && fabs(lb - ub) < 1e-9 * (1.0 + fabs(lb))) { type = LPX_FX; if (fabs(lb) <= fabs(ub)) ub = lb; else lb = ub; } lpx_set_col_bnds(lp, j, type, lb, ub); } /* load the constraint matrix */ ind = ucalloc(1+n, sizeof(int)); val = ucalloc(1+n, sizeof(double)); for (i = 1; i <= m; i++) { len = mpl_get_mat_row(mpl, i, ind, val); lpx_set_mat_row(lp, i, len, ind, val); } /* build objective function (the first objective is used) */ for (i = 1; i <= m; i++) { kind = mpl_get_row_kind(mpl, i); if (kind == MPL_MIN || kind == MPL_MAX) { /* set objective name */ lpx_set_obj_name(lp, mpl_get_row_name(mpl, i)); /* set optimization direction */ lpx_set_obj_dir(lp, kind == MPL_MIN ? LPX_MIN : LPX_MAX); /* set constant term */ lpx_set_obj_coef(lp, 0, mpl_get_row_c0(mpl, i)); /* set objective coefficients */ len = mpl_get_mat_row(mpl, i, ind, val); for (t = 1; t <= len; t++) lpx_set_obj_coef(lp, ind[t], val[t]); break; } } /* free working arrays */ ufree(ind); ufree(val); /* bring the problem object to the calling program */ return lp; }
int load_overlay_data(Overlay_t **over, int num_overlays) { int i,j; int index,found; int len,point; int num_points; int num_fields; /* number of fields (tokens) founs in input line */ double field[16]; /* space for numerical fields */ char buf[256]; /* Buffer for input lines */ FILE *infile; char *cfield[32]; Overlay_t *ov; /* pointer to the current overlay structure */ for(i=0; i < 32; i++) cfield[i] = (char *) ucalloc(1,64); /* get space for sub strings */ /* Read in the data points for each overlay file */ for(i=0; i < num_overlays; i++) { ov = over[i]; ov->num_polylines = 0; ov->num_labels = 0; ov->num_icons = 0; if((infile = fopen(ov->map_file_name,"r")) == NULL) { fprintf(stderr,"Warning!: Unable to find map file: %s\n",ov->map_file_name); } else { while(fgets(buf,256,infile) != NULL) { /* read all lines in file */ if(buf[0] == '#') continue; if(strncmp(buf,"MAP_NAME",8) == 0) { /* Currently Ignore */ continue; } if(strncmp(buf,"TRANSFORM",9) == 0) { /* Currently Ignore */ continue; } if(strncmp(buf,"PROJECTION",10) == 0) { /* Currently Ignore */ continue; } if(strncmp(buf,"ICONDEF",7) == 0) { /* describes an icon's coordinates in pixels */ index = ov->num_icondefs; if(index >= ov->num_alloc_icondefs) { if(ov->num_alloc_icondefs == 0) { /* start with space for 2 */ ov->geo_icondef = (Geo_feat_icondef_t **) ucalloc(2,sizeof(Geo_feat_icondef_t *)); ov->num_alloc_icondefs = 2; } else { /* Double the space */ ov->num_alloc_icondefs *= 2; ov->geo_icondef = (Geo_feat_icondef_t **) urealloc(ov->geo_icondef, ov->num_alloc_icondefs * sizeof(Geo_feat_icondef_t *)); } } if(ov->geo_icondef == NULL) { fprintf(stderr,"Unable to allocate memory for Icon definition pointer array!\n"); exit(-1); } if(STRparse(buf,cfield,256,32,64) != 3) { fprintf(stderr,"Error in ICONDEF line: %s\n",buf); exit(-1); } /* get space for the icon definition */ ov->geo_icondef[index] = (Geo_feat_icondef_t *) ucalloc(1,sizeof(Geo_feat_icondef_t)); ZERO_STRUCT(ov->geo_icondef[index]); if(ov->geo_icondef[index] == NULL) { fprintf(stderr,"Unable to allocate memory for Icon definition!\n"); exit(-1); } STRcopy(ov->geo_icondef[index]->name,cfield[1],NAME_LENGTH); num_points = atoi(cfield[2]); /* Get space for points in the icon */ ov->geo_icondef[index]->x = (short *) ucalloc(1,num_points * sizeof(short)); ov->geo_icondef[index]->y = (short *) ucalloc(1,num_points * sizeof(short)); if(ov->geo_icondef[index]->x == NULL || ov->geo_icondef[index]->y == NULL) { fprintf(stderr,"Error!: Unable to allocate space for icon points in file %s, num points: %d\n", ov->map_file_name,num_points); exit(-1); } /* Read in all of the points */ for(j=0,point = 0; j < num_points; j++) { if(fgets(buf,256,infile) == NULL) continue; if(STRparse(buf,cfield,256,32,64) == 2) { ov->geo_icondef[index]->x[point] = atoi(cfield[0]); ov->geo_icondef[index]->y[point] = atoi(cfield[1]); point++; } } ov->geo_icondef[index]->num_points = point; ov->num_icondefs++; continue; } if(strncmp(buf,"ICON ",5) == 0) { index = ov->num_icons; if(index >= ov->num_alloc_icons) { if(ov->num_alloc_icons == 0) { /* start with space for 2 */ ov->geo_icon = (Geo_feat_icon_t **) ucalloc(2,sizeof(Geo_feat_icon_t *)); ov->num_alloc_icons = 2; } else { /* Double the space */ ov->num_alloc_icons *= 2; ov->geo_icon = (Geo_feat_icon_t **) urealloc(ov->geo_icon, ov->num_alloc_icons * sizeof(Geo_feat_icon_t *)); } } if(ov->geo_icon == NULL) { fprintf(stderr,"Unable to allocate memory for Icon pointer array!\n"); exit(-1); } /* get space for the Icon */ ov->geo_icon[index] = (Geo_feat_icon_t *) ucalloc(1,sizeof(Geo_feat_icon_t)); ZERO_STRUCT(ov->geo_icon[index]); if(ov->geo_icon[index] == NULL) { fprintf(stderr,"Unable to allocate memory for Icon definition!\n"); exit(-1); } if((num_fields = STRparse(buf,cfield,256,32,64)) < 6) { fprintf(stderr,"Error in ICON line: %s\n",buf); exit(-1); } /* find the definition for the line segments that make up the icon */ ov->geo_icon[index]->icon = NULL; found = 0; for(j=0; j < ov->num_icondefs && found == 0; j++) { if(strcmp(ov->geo_icondef[j]->name,cfield[1]) == 0) { ov->geo_icon[index]->icon = ov->geo_icondef[j]; found = 1; } } if(found == 0) { fprintf(stderr,"No Icon definition: %s found in file %s!\n",cfield[1],ov->map_file_name); continue; } /* record its position */ ov->geo_icon[index]->lat = atof(cfield[2]); ov->geo_icon[index]->lon = atof(cfield[3]); ov->geo_icon[index]->text_x = atoi(cfield[4]); ov->geo_icon[index]->text_y = atoi(cfield[5]); /* gather up remaining text fields */ ov->geo_icon[index]->label[0] = '\0'; len = 0; for(j = 6; j < num_fields; j++ ) { strncat(ov->geo_icon[index]->label,cfield[j],LABEL_LENGTH - len); len = strlen(ov->geo_icon[index]->label) +1; strncat(ov->geo_icon[index]->label," ",LABEL_LENGTH - len); len = strlen(ov->geo_icon[index]->label) +1; } ov->num_icons++; continue; } if(strncmp(buf,"POLYLINE",8) == 0) { index = ov->num_polylines; if(index >= ov->num_alloc_polylines) { if(ov->num_alloc_polylines == 0) { /* start with space for 2 */ ov->geo_polyline = (Geo_feat_polyline_t **) ucalloc(2,sizeof(Geo_feat_polyline_t *)); ov->num_alloc_polylines = 2; } else { /* Double the space */ ov->num_alloc_polylines *= 2; ov->geo_polyline = (Geo_feat_polyline_t **) urealloc(ov->geo_polyline, ov->num_alloc_polylines * sizeof(Geo_feat_polyline_t *)); } } if(ov->geo_polyline == NULL) { fprintf(stderr,"Unable to allocate memory for Polyline pointer array!\n"); exit(-1); } if((STRparse(buf,cfield,256,32,64)) != 3) { fprintf(stderr,"Error in POLYLINE line: %s\n",buf); exit(-1); } /* get space for the Polyline definition */ ov->geo_polyline[index] = (Geo_feat_polyline_t *) ucalloc(1,sizeof(Geo_feat_polyline_t)); ZERO_STRUCT(ov->geo_polyline[index]); if(ov->geo_polyline[index] == NULL) { fprintf(stderr,"Unable to allocate memory for Polyline definition!\n"); exit(-1); } STRcopy(ov->geo_polyline[index]->label,cfield[1],LABEL_LENGTH); num_points = atoi(cfield[2]); /* Get space for points in the icon */ ov->geo_polyline[index]->lat = (double *) ucalloc(1,num_points * sizeof(double)); ov->geo_polyline[index]->lon = (double *) ucalloc(1,num_points * sizeof(double)); ov->geo_polyline[index]->local_x = (double *) ucalloc(1,num_points * sizeof(double)); ov->geo_polyline[index]->local_y = (double *) ucalloc(1,num_points * sizeof(double)); if(ov->geo_polyline[index]->lat == NULL || ov->geo_polyline[index]->lon == NULL) { fprintf(stderr,"Error!: Unable to allocate space for polyline points in file %s, num points: %d\n", ov->map_file_name,num_points); exit(-1); } /* Read in all of the points */ for(j=0,point = 0; j < num_points; j++) { if(fgets(buf,256,infile) == NULL) continue; if(STRparse(buf,cfield,256,32,64) == 2) { ov->geo_polyline[index]->lat[point] = atof(cfield[0]); ov->geo_polyline[index]->lon[point] = atof(cfield[1]); point++; } } ov->geo_polyline[index]->num_points = point; ov->num_polylines++; continue; } if(strncmp(buf,"LABEL",5) == 0) { index = ov->num_labels; if(index >= ov->num_alloc_labels) { if(ov->num_alloc_labels == 0) { /* start with space for 2 */ ov->geo_label = (Geo_feat_label_t **) ucalloc(2,sizeof(Geo_feat_label_t *)); ov->num_alloc_labels = 2; } else { /* Double the space */ ov->num_alloc_labels *=2; ov->geo_label = (Geo_feat_label_t **) urealloc(ov->geo_label, ov->num_alloc_labels * sizeof(Geo_feat_label_t *)); } } if(ov->geo_label == NULL) { fprintf(stderr,"Unable to allocate memory for Label pointer array!\n"); exit(-1); } ov->num_labels++; /* get space for the Label definition */ ov->geo_label[index] = (Geo_feat_label_t *) ucalloc(1,sizeof(Geo_feat_label_t)); ZERO_STRUCT(ov->geo_label[index]); if(ov->geo_label[index] == NULL) { fprintf(stderr,"Unable to allocate memory for Label definition!\n"); exit(-1); } if((num_fields = STRparse(buf,cfield,256,32,64)) < 8) { fprintf(stderr,"Too few fields in LABEL line: %s\n",buf); continue; } ov->geo_label[index]->min_lat = atof(cfield[1]); ov->geo_label[index]->min_lon = atof(cfield[2]); ov->geo_label[index]->max_lat = atof(cfield[3]); ov->geo_label[index]->max_lon = atof(cfield[4]); ov->geo_label[index]->rotation = atof(cfield[5]); ov->geo_label[index]->attach_lat = atof(cfield[6]); ov->geo_label[index]->attach_lon = atof(cfield[7]); ov->geo_label[index]->string[0] = '\0'; len = 0; for(j = 8; j < num_fields; j++) { strncat(ov->geo_label[index]->string,cfield[j],NAME_LENGTH - len); len = strlen(ov->geo_label[index]->string) +1; strncat(ov->geo_label[index]->string," ",NAME_LENGTH - len); len = strlen(ov->geo_label[index]->string) +1; } continue; } if(strncmp(buf,"SIMPLELABEL",11) == 0) { index = ov->num_labels; if(index >= ov->num_alloc_labels) { if(ov->num_alloc_labels == 0) { /* start with space for 2 */ ov->geo_label = (Geo_feat_label_t **) ucalloc(2,sizeof(Geo_feat_label_t *)); ov->num_alloc_labels = 2; } else { /* Double the space */ ov->num_alloc_labels *=2; ov->geo_label = (Geo_feat_label_t **) urealloc(ov->geo_label, ov->num_alloc_labels * sizeof(Geo_feat_label_t *)); } } if(ov->geo_label == NULL) { fprintf(stderr,"Unable to allocate memory for Label pointer array!\n"); exit(-1); } ov->num_labels++; /* get space for the Label definition */ ov->geo_label[index] = (Geo_feat_label_t *) ucalloc(1,sizeof(Geo_feat_label_t)); ZERO_STRUCT(ov->geo_label[index]); if(ov->geo_label[index] == NULL) { fprintf(stderr,"Unable to allocate memory for Label definition!\n"); exit(-1); } if((num_fields = STRparse(buf,cfield,256,32,64)) < 4) { fprintf(stderr,"Too few fields in SIMPLELABEL line: %s\n",buf); continue; } ov->geo_label[index]->min_lat = atof(cfield[1]); ov->geo_label[index]->min_lon = atof(cfield[2]); ov->geo_label[index]->max_lat = atof(cfield[1]); ov->geo_label[index]->max_lon = atof(cfield[2]); ov->geo_label[index]->rotation = 0; ov->geo_label[index]->attach_lat = atof(cfield[1]); ov->geo_label[index]->attach_lon = atof(cfield[2]); ov->geo_label[index]->string[0] = '\0'; len = 0; for(j = 3; j < num_fields; j++) { strncat(ov->geo_label[index]->string,cfield[j],NAME_LENGTH - len); len = strlen(ov->geo_label[index]->string) +1; strncat(ov->geo_label[index]->string," ",NAME_LENGTH - len); len = strlen(ov->geo_label[index]->string) +1; } continue; } } if(gd.debug) printf("Overlay File %s contains %d Polylines, %d Icon_defns, %d Icons, %d Labels\n", ov->map_file_name,ov->num_polylines,ov->num_icondefs,ov->num_icons,ov->num_labels); fclose(infile); } } for(i=0; i < 32; i++) ufree(cfield[i]); /* free space for sub strings */ return SUCCESS; }
si32 fill_cvars() { si32 i, ifld=0; ui08 filename[BUF_SIZE]; ui08 buf[BUF_SIZE]; FILE *fp; /**********************************************************************/ if (Glob->params.debug) fprintf(stderr, "--------fill_cvars------------- \n\n"); /* get memory for calculated variable table -- kept for duration of run */ Glob->cv = (CalculatedVariables *) ucalloc(MAX_CALC_FIELDS,(unsigned) sizeof(CalculatedVariables)); /* make filename for calcualted variables table */ sprintf(filename, Glob->params.cvars_file_path); if (Glob->params.debug) fprintf(stderr, "Calculated Variables table filename is %s \n",filename); /* open the file */ if ((fp = fopen(filename,"r")) == NULL) { exit_str("Could not open calculated variables file"); } /* read each line and extract field names, variable type and coefficients */ while (fgets(buf,BUF_SIZE,fp) != NULL) { if (buf[0] != COMMENT_CHAR) { sscanf(buf,"%s %s %lf %lf %lf %lf \n", Glob->cv[ifld].name, Glob->cv[ifld].var_type, &Glob->cv[ifld].c1, &Glob->cv[ifld].c2, &Glob->cv[ifld].c3, &Glob->cv[ifld].c4); /* fill in unknown for units, this will be filled in later * by individual calc_* functions */ strncpy(Glob->cv[ifld].units,"UNKNOWN ",8); /* fill in var_type with blanks so no null byte in first 8 chars */ for (i = strlen(Glob->cv[ifld].var_type); i < 8; i++) { memcpy(&Glob->cv[ifld].var_type[i]," ",1); } ifld ++; /* exit if there isn't enough memory for calc variables table */ if (ifld > MAX_CALC_FIELDS) exit_str("Not enough memory allocated for Calculated Variables Table"); } } /* end reading data */ /* set the total number of calculated fields */ Glob->num_calc_fields = ifld; /* print out calculated variables table info */ if (Glob->params.debug) { fprintf(stderr, "name f_type c1 c2 c3\n"); for (i = 0; i < Glob->num_calc_fields; i++) { fprintf(stderr, "%3d %s %s %f %f %f %f \n", i, Glob->cv[i].name, Glob->cv[i].var_type, Glob->cv[i].c1, Glob->cv[i].c2, Glob->cv[i].c3, Glob->cv[i].c4); } fprintf(stderr, "---------------------------------- \n\n"); } /* endif if debug and printing */ fclose(fp); return(OKAY); }
int spx_prim_feas(SPX *spx) { /* find primal feasible solution (primal simplex) */ int m = spx->m; int n = spx->n; int i, k, ret; double sum_0; double start = utime(), spent = 0.0; /* the initial basis should be "warmed up" */ if (spx->b_stat != LPX_B_VALID || spx->p_stat == LPX_P_UNDEF || spx->d_stat == LPX_D_UNDEF) { ret = LPX_E_BADB; goto done; } /* if the initial basic solution is primal feasible, nothing to search for */ if (spx->p_stat == LPX_P_FEAS) { ret = LPX_E_OK; goto done; } /* allocate the working segment */ insist(spx->meth == 0); spx->meth = 'P'; spx->p = 0; spx->p_tag = 0; spx->q = 0; spx->zeta = ucalloc(1+m, sizeof(double)); spx->ap = ucalloc(1+n, sizeof(double)); spx->aq = ucalloc(1+m, sizeof(double)); spx->gvec = ucalloc(1+n, sizeof(double)); spx->dvec = NULL; spx->refsp = (spx->price ? ucalloc(1+m+n, sizeof(int)) : NULL); spx->count = 0; spx->work = ucalloc(1+m+n, sizeof(double)); spx->orig_typx = ucalloc(1+m+n, sizeof(int)); spx->orig_lb = ucalloc(1+m+n, sizeof(double)); spx->orig_ub = ucalloc(1+m+n, sizeof(double)); spx->orig_dir = 0; spx->orig_coef = ucalloc(1+m+n, sizeof(double)); /* save components of the original LP problem, which are changed by the routine */ memcpy(spx->orig_typx, spx->typx, (1+m+n) * sizeof(int)); memcpy(spx->orig_lb, spx->lb, (1+m+n) * sizeof(double)); memcpy(spx->orig_ub, spx->ub, (1+m+n) * sizeof(double)); spx->orig_dir = spx->dir; memcpy(spx->orig_coef, spx->coef, (1+m+n) * sizeof(double)); /* build an artificial basic solution, which is primal feasible, and also build an auxiliary objective function to minimize the sum of infeasibilities (residuals) for the original problem */ spx->dir = LPX_MIN; for (k = 0; k <= m+n; k++) spx->coef[k] = 0.0; for (i = 1; i <= m; i++) { int typx_k; double lb_k, ub_k, bbar_i; double eps = 0.10 * spx->tol_bnd; k = spx->indx[i]; /* x[k] = xB[i] */ typx_k = spx->orig_typx[k]; lb_k = spx->orig_lb[k]; ub_k = spx->orig_ub[k]; bbar_i = spx->bbar[i]; if (typx_k == LPX_LO || typx_k == LPX_DB || typx_k == LPX_FX) { /* in the original problem x[k] has an lower bound */ if (bbar_i < lb_k - eps) { /* and violates it */ spx->typx[k] = LPX_UP; spx->lb[k] = 0.0; spx->ub[k] = lb_k; spx->coef[k] = -1.0; /* x[k] should be increased */ } } if (typx_k == LPX_UP || typx_k == LPX_DB || typx_k == LPX_FX) { /* in the original problem x[k] has an upper bound */ if (bbar_i > ub_k + eps) { /* and violates it */ spx->typx[k] = LPX_LO; spx->lb[k] = ub_k; spx->ub[k] = 0.0; spx->coef[k] = +1.0; /* x[k] should be decreased */ } } } /* now the initial basic solution should be primal feasible due to changes of bounds of some basic variables, which turned to implicit artifical variables */ insist(spx_check_bbar(spx, spx->tol_bnd) == 0.0); /* compute the initial sum of infeasibilities for the original problem */ sum_0 = orig_infsum(spx, 0.0); /* it can't be zero, because the initial basic solution is primal infeasible */ insist(sum_0 != 0.0); /* compute simplex multipliers and reduced costs of non-basic variables once again (because the objective function has been changed) */ spx_eval_pi(spx); spx_eval_cbar(spx); /* initialize weights of non-basic variables */ if (!spx->price) { /* textbook pricing will be used */ int j; for (j = 1; j <= n; j++) spx->gvec[j] = 1.0; } else { /* steepest edge pricing will be used */ spx_reset_refsp(spx); } /* display information about the initial basic solution */ if (spx->msg_lev >= 2 && spx->it_cnt % spx->out_frq != 0 && spx->out_dly <= spent) prim_feas_dpy(spx, sum_0); /* main loop starts here */ for (;;) { /* determine the spent amount of time */ spent = utime() - start; /* display information about the current basic solution */ if (spx->msg_lev >= 2 && spx->it_cnt % spx->out_frq == 0 && spx->out_dly <= spent) prim_feas_dpy(spx, sum_0); /* we needn't to wait until all artificial variables leave the basis */ if (orig_infsum(spx, spx->tol_bnd) == 0.0) { /* the sum of infeasibilities is zero, therefore the current solution is primal feasible for the original problem */ ret = LPX_E_OK; break; } /* check if the iterations limit has been exhausted */ if (spx->it_lim == 0) { ret = LPX_E_ITLIM; break; } /* check if the time limit has been exhausted */ if (spx->tm_lim >= 0.0 && spx->tm_lim <= spent) { ret = LPX_E_TMLIM; break; } /* choose non-basic variable xN[q] */ if (spx_prim_chuzc(spx, spx->tol_dj)) { /* basic solution components were recomputed; check primal feasibility (of the artificial solution) */ if (spx_check_bbar(spx, spx->tol_bnd) != 0.0) { /* the current solution became primal infeasible due to round-off errors */ ret = LPX_E_INSTAB; break; } } /* if no xN[q] has been chosen, the sum of infeasibilities is minimal but non-zero; therefore the original problem has no primal feasible solution */ if (spx->q == 0) { ret = LPX_E_NOFEAS; break; } /* compute the q-th column of the current simplex table (later this column will enter the basis) */ spx_eval_col(spx, spx->q, spx->aq, 1); /* choose basic variable xB[p] */ if (spx_prim_chuzr(spx, spx->relax * spx->tol_bnd)) { /* the basis matrix should be reinverted, because the q-th column of the simplex table is unreliable */ insist("not implemented yet" == NULL); } /* the sum of infeasibilities can't be negative, therefore the modified problem can't have unbounded solution */ insist(spx->p != 0); /* update values of basic variables */ spx_update_bbar(spx, NULL); if (spx->p > 0) { /* compute the p-th row of the inverse inv(B) */ spx_eval_rho(spx, spx->p, spx->zeta); /* compute the p-th row of the current simplex table */ spx_eval_row(spx, spx->zeta, spx->ap); /* update simplex multipliers */ spx_update_pi(spx); /* update reduced costs of non-basic variables */ spx_update_cbar(spx, 0); /* update weights of non-basic variables */ if (spx->price) spx_update_gvec(spx); } /* xB[p] is leaving the basis; if it is implicit artificial variable, the corresponding residual vanishes; therefore bounds of this variable should be restored to the original ones */ if (spx->p > 0) { k = spx->indx[spx->p]; /* x[k] = xB[p] */ if (spx->typx[k] != spx->orig_typx[k]) { /* x[k] is implicit artificial variable */ spx->typx[k] = spx->orig_typx[k]; spx->lb[k] = spx->orig_lb[k]; spx->ub[k] = spx->orig_ub[k]; insist(spx->p_tag == LPX_NL || spx->p_tag == LPX_NU); spx->p_tag = (spx->p_tag == LPX_NL ? LPX_NU : LPX_NL); if (spx->typx[k] == LPX_FX) spx->p_tag = LPX_NS; /* nullify the objective coefficient at x[k] */ spx->coef[k] = 0.0; /* since coef[k] has been changed, we need to compute new reduced cost of x[k], which it will have in the adjacent basis */ /* the formula d[j] = cN[j] - pi' * N[j] is used (note that the vector pi is not changed, because it depends on objective coefficients at basic variables, but in the adjacent basis, for which the vector pi has been just recomputed, x[k] is non-basic) */ if (k <= m) { /* x[k] is auxiliary variable */ spx->cbar[spx->q] = - spx->pi[k]; } else { /* x[k] is structural variable */ int ptr = spx->aa_ptr[k]; int end = ptr + spx->aa_len[k] - 1; double d = 0.0; for (ptr = ptr; ptr <= end; ptr++) d += spx->pi[spx->aa_ind[ptr]] * spx->aa_val[ptr]; spx->cbar[spx->q] = d; } } } /* jump to the adjacent vertex of the LP polyhedron */ if (spx_change_basis(spx)) { /* the basis matrix should be reinverted */ if (spx_invert(spx)) { /* numerical problems with the basis matrix */ ret = LPX_E_SING; break; } /* compute the current basic solution components */ spx_eval_bbar(spx); spx_eval_pi(spx); spx_eval_cbar(spx); /* check primal feasibility */ if (spx_check_bbar(spx, spx->tol_bnd) != 0.0) { /* the current solution became primal infeasible due to excessive round-off errors */ ret = LPX_E_INSTAB; break; } } #if 0 /* check accuracy of main solution components after updating (for debugging purposes only) */ { double ae_bbar = spx_err_in_bbar(spx); double ae_pi = spx_err_in_pi(spx); double ae_cbar = spx_err_in_cbar(spx, 0); double ae_gvec = spx->price ? spx_err_in_gvec(spx) : 0.0; print("bbar: %g; pi: %g; cbar: %g; gvec: %g", ae_bbar, ae_pi, ae_cbar, ae_gvec); if (ae_bbar > 1e-7 || ae_pi > 1e-7 || ae_cbar > 1e-7 || ae_gvec > 1e-3) fault("solution accuracy too low"); } #endif } /* restore components of the original problem, which were changed by the routine */ memcpy(spx->typx, spx->orig_typx, (1+m+n) * sizeof(int)); memcpy(spx->lb, spx->orig_lb, (1+m+n) * sizeof(double)); memcpy(spx->ub, spx->orig_ub, (1+m+n) * sizeof(double)); spx->dir = spx->orig_dir; memcpy(spx->coef, spx->orig_coef, (1+m+n) * sizeof(double)); /* if there are numerical problems with the basis matrix, the latter must be repaired; mark the basic solution as undefined and exit immediately */ if (ret == LPX_E_SING) { spx->p_stat = LPX_P_UNDEF; spx->d_stat = LPX_D_UNDEF; goto done; } /* compute the final basic solution components */ spx_eval_bbar(spx); spx_eval_pi(spx); spx_eval_cbar(spx); if (spx_check_bbar(spx, spx->tol_bnd) == 0.0) spx->p_stat = LPX_P_FEAS; else spx->p_stat = LPX_P_INFEAS; if (spx_check_cbar(spx, spx->tol_dj) == 0.0) spx->d_stat = LPX_D_FEAS; else spx->d_stat = LPX_D_INFEAS; /* display information about the final basic solution */ if (spx->msg_lev >= 2 && spx->it_cnt % spx->out_frq != 0 && spx->out_dly <= spent) prim_feas_dpy(spx, sum_0); /* correct the preliminary diagnosis */ switch (ret) { case LPX_E_OK: /* assumed LPX_P_FEAS */ if (spx->p_stat != LPX_P_FEAS) ret = LPX_E_INSTAB; break; case LPX_E_ITLIM: case LPX_E_TMLIM: /* assumed LPX_P_INFEAS */ if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; break; case LPX_E_NOFEAS: /* assumed LPX_P_INFEAS */ if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; else spx->p_stat = LPX_P_NOFEAS; break; case LPX_E_INSTAB: /* assumed LPX_P_INFEAS */ if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; break; default: insist(ret != ret); } done: /* deallocate the working segment */ if (spx->meth != 0) { spx->meth = 0; ufree(spx->zeta); ufree(spx->ap); ufree(spx->aq); ufree(spx->gvec); if (spx->price) ufree(spx->refsp); ufree(spx->work); ufree(spx->orig_typx); ufree(spx->orig_lb); ufree(spx->orig_ub); ufree(spx->orig_coef); } /* determine the spent amount of time */ spent = utime() - start; /* decrease the time limit by the spent amount */ if (spx->tm_lim >= 0.0) { spx->tm_lim -= spent; if (spx->tm_lim < 0.0) spx->tm_lim = 0.0; } /* return to the calling program */ return ret; }
static void transform(struct dsa *dsa) { /* transform original LP to standard formulation */ LPX *lp = dsa->lp; int orig_m = dsa->orig_m; int orig_n = dsa->orig_n; int *ref = dsa->ref; int m = dsa->m; int n = dsa->n; double *b = dsa->b; double *c = dsa->c; int i, j, k, type, t, ii, len, *ind; double lb, ub, coef, rii, sjj, *val; /* initialize components of transformed LP */ dsa->ne = 0; for (i = 1; i <= m; i++) b[i] = 0.0; c[0] = lpx_get_obj_coef(lp, 0); for (j = 1; j <= n; j++) c[j] = 0.0; /* i and j are, respectively, ordinal number of current row and ordinal number of current column in transformed LP */ i = j = 0; /* transform rows (auxiliary variables) */ for (k = 1; k <= orig_m; k++) { type = lpx_get_row_type(lp, k); rii = lpx_get_rii(lp, k); lb = lpx_get_row_lb(lp, k) * rii; ub = lpx_get_row_ub(lp, k) * rii; switch (type) { case LPX_FR: /* source: -inf < (L.F.) < +inf */ /* result: ignore free row */ ref[k] = 0; break; case LPX_LO: /* source: lb <= (L.F.) < +inf */ /* result: (L.F.) - x' = lb, x' >= 0 */ i++; j++; ref[k] = i; new_coef(dsa, i, j, -1.0); b[i] = lb; break; case LPX_UP: /* source: -inf < (L.F.) <= ub */ /* result: (L.F.) + x' = ub, x' >= 0 */ i++; j++; ref[k] = i; new_coef(dsa, i, j, +1.0); b[i] = ub; break; case LPX_DB: /* source: lb <= (L.F.) <= ub */ /* result: (L.F.) - x' = lb, x' + x'' = ub - lb */ i++; j++; ref[k] = i; new_coef(dsa, i, j, -1.0); b[i] = lb; i++; new_coef(dsa, i, j, +1.0); j++; new_coef(dsa, i, j, +1.0); b[i] = ub - lb; break; case LPX_FX: /* source: (L.F.) = lb */ /* result: (L.F.) = lb */ i++; ref[k] = i; b[i] = lb; break; default: insist(type != type); } } /* transform columns (structural variables) */ ind = ucalloc(1+orig_m, sizeof(int)); val = ucalloc(1+orig_m, sizeof(double)); for (k = 1; k <= orig_n; k++) { type = lpx_get_col_type(lp, k); sjj = lpx_get_sjj(lp, k); lb = lpx_get_col_lb(lp, k) / sjj; ub = lpx_get_col_ub(lp, k) / sjj; coef = lpx_get_obj_coef(lp, k) * sjj; len = lpx_get_mat_col(lp, k, ind, val); for (t = 1; t <= len; t++) val[t] *= (lpx_get_rii(lp, ind[t]) * sjj); switch (type) { case LPX_FR: /* source: -inf < x < +inf */ /* result: x = x' - x'', x' >= 0, x'' >= 0 */ j++; ref[orig_m+k] = j; for (t = 1; t <= len; t++) { ii = ref[ind[t]]; if (ii != 0) new_coef(dsa, ii, j, +val[t]); } c[j] = +coef; j++; for (t = 1; t <= len; t++) { ii = ref[ind[t]]; if (ii != 0) new_coef(dsa, ii, j, -val[t]); } c[j] = -coef; break; case LPX_LO: /* source: lb <= x < +inf */ /* result: x = lb + x', x' >= 0 */ j++; ref[orig_m+k] = j; for (t = 1; t <= len; t++) { ii = ref[ind[t]]; if (ii != 0) { new_coef(dsa, ii, j, val[t]); b[ii] -= val[t] * lb; } } c[j] = +coef; c[0] += c[j] * lb; break; case LPX_UP: /* source: -inf < x <= ub */ /* result: x = ub - x', x' >= 0 */ j++; ref[orig_m+k] = j; for (t = 1; t <= len; t++) { ii = ref[ind[t]]; if (ii != 0) { new_coef(dsa, ii, j, -val[t]); b[ii] -= val[t] * ub; } } c[j] = -coef; c[0] -= c[j] * ub; break; case LPX_DB: /* source: lb <= x <= ub */ /* result: x = lb + x', x' + x'' = ub - lb */ j++; ref[orig_m+k] = j; for (t = 1; t <= len; t++) { ii = ref[ind[t]]; if (ii != 0) { new_coef(dsa, ii, j, val[t]); b[ii] -= val[t] * lb; } } c[j] = +coef; c[0] += c[j] * lb; i++; new_coef(dsa, i, j, +1.0); j++; new_coef(dsa, i, j, +1.0); b[i] = ub - lb; break; case LPX_FX: /* source: x = lb */ /* result: just substitute */ ref[orig_m+k] = 0; for (t = 1; t <= len; t++) { ii = ref[ind[t]]; if (ii != 0) b[ii] -= val[t] * lb; } c[0] += coef * lb; break; default: insist(type != type); } } ufree(ind); ufree(val); /* end of transformation */ insist(i == m && j == n); /* change the objective sign in case of maximization */ if (lpx_get_obj_dir(lp) == LPX_MAX) for (j = 0; j <= n; j++) c[j] = -c[j]; return; }
MDV_master_header_t *RfCreateMdvMasterHdr(vol_file_handle_t *v_handle, char *calling_routine) { char calling_sequence[MAX_SEQ]; MDV_master_header_t *master_hdr = NULL; int proj_type; /* * set up calling sequence */ sprintf(calling_sequence, "%s:%s", calling_routine, THIS_ROUTINE); /* * Determine the projection type for use in calculating other fields. */ if (strstr(v_handle->vol_params->cart.unitsy, "deg")) proj_type = MDV_PROJ_POLAR_RADAR; else { if (v_handle->vol_params->cart.scalex != v_handle->vol_params->cart.km_scalex) proj_type = MDV_PROJ_LATLON; else proj_type = MDV_PROJ_FLAT; } /* * Allocate space for the master header. */ master_hdr = (MDV_master_header_t *)ucalloc(1, sizeof(MDV_master_header_t)); /* * Update the fields in the header */ master_hdr->record_len1 = sizeof(MDV_master_header_t) - (2 * sizeof(si32)); master_hdr->struct_id = MDV_MASTER_HEAD_MAGIC_COOKIE; master_hdr->revision_number = MDV_REVISION_NUMBER; master_hdr->time_gen = Rfrtime2utime(&v_handle->vol_params->file_time); master_hdr->time_begin = Rfrtime2utime(&v_handle->vol_params->start_time); master_hdr->time_end = Rfrtime2utime(&v_handle->vol_params->end_time); master_hdr->time_centroid = Rfrtime2utime(&v_handle->vol_params->mid_time); master_hdr->time_expire = master_hdr->time_end; master_hdr->num_data_times = 0; master_hdr->index_number = 0; master_hdr->data_dimension = 3; master_hdr->data_collection_type = MDV_DATA_MEASURED; master_hdr->native_vlevel_type = MDV_VERT_TYPE_ELEV; if (strstr(v_handle->vol_params->cart.unitsz, "deg")) { master_hdr->vlevel_type = MDV_VERT_TYPE_ELEV; } else { master_hdr->vlevel_type = MDV_VERT_TYPE_Z; } master_hdr->vlevel_included = TRUE; master_hdr->grid_order_direction = MDV_ORIENT_SN_WE; master_hdr->grid_order_indices = MDV_ORDER_XYZ; master_hdr->n_fields = v_handle->vol_params->nfields; master_hdr->max_nx = v_handle->vol_params->cart.nx; master_hdr->max_ny = v_handle->vol_params->cart.ny; master_hdr->max_nz = v_handle->vol_params->cart.nz; if (v_handle->vol_params->radar.nelevations <= 0) master_hdr->n_chunks = 1; /* just vol params */ else master_hdr->n_chunks = 2; /* vol params and elevations */ master_hdr->field_hdr_offset = 0; master_hdr->vlevel_hdr_offset = 0; master_hdr->chunk_hdr_offset = 0; if (proj_type == MDV_PROJ_LATLON) { master_hdr->sensor_lon = UNSCALE_INT(v_handle->vol_params->cart.radarx, v_handle->vol_params->cart.scalex); master_hdr->sensor_lat = UNSCALE_INT(v_handle->vol_params->cart.radary, v_handle->vol_params->cart.scaley); } else { double sensor_lat; double sensor_lon; PJGstruct *pjg_struct = PJGs_flat_init(UNSCALE_INT(v_handle->vol_params->cart.latitude, 1000000), UNSCALE_INT(v_handle->vol_params->cart.longitude, 1000000), UNSCALE_INT(v_handle->vol_params->cart.rotation, 1000000)); PJGs_flat_xy2latlon(pjg_struct, UNSCALE_INT(v_handle->vol_params->cart.radarx, v_handle->vol_params->cart.scalex), UNSCALE_INT(v_handle->vol_params->cart.radary, v_handle->vol_params->cart.scaley), &(sensor_lat), &(sensor_lon)); master_hdr->sensor_lat = sensor_lat; master_hdr->sensor_lon = sensor_lon; } master_hdr->sensor_alt = UNSCALE_INT(v_handle->vol_params->cart.radarz, v_handle->vol_params->cart.scalez); strncpy((char *)master_hdr->data_set_info, v_handle->vol_params->note, MDV_INFO_LEN); master_hdr->data_set_info[MDV_INFO_LEN-1] = '\0'; strncpy((char *)master_hdr->data_set_name, v_handle->vol_file_label, MDV_NAME_LEN); master_hdr->data_set_name[MDV_NAME_LEN-1] = '\0'; if (v_handle->vol_file_path == (char *)NULL) master_hdr->data_set_source[0] = '\0'; else strncpy((char *)master_hdr->data_set_source, v_handle->vol_file_path, MDV_NAME_LEN); master_hdr->data_set_source[MDV_NAME_LEN-1] = '\0'; master_hdr->record_len2 = master_hdr->record_len1; return(master_hdr); }
static int triang(int m, int n, void *info, int (*mat)(void *info, int k, int ndx[]), int rn[], int cn[]) { int *ndx; /* int ndx[1+max(m,n)]; */ /* this array is used for querying row and column patterns of the given matrix A (the third parameter to the routine mat) */ int *rs_len; /* int rs_len[1+m]; */ /* rs_len[0] is not used; rs_len[i], 1 <= i <= m, is number of non-zeros in the i-th row of the matrix A, which (non-zeros) belong to the current active submatrix */ int *rs_head; /* int rs_head[1+n]; */ /* rs_head[len], 0 <= len <= n, is the number i of the first row of the matrix A, for which rs_len[i] = len */ int *rs_prev; /* int rs_prev[1+m]; */ /* rs_prev[0] is not used; rs_prev[i], 1 <= i <= m, is a number i' of the previous row of the matrix A, for which rs_len[i] = rs_len[i'] (zero marks the end of this linked list) */ int *rs_next; /* int rs_next[1+m]; */ /* rs_next[0] is not used; rs_next[i], 1 <= i <= m, is a number i' of the next row of the matrix A, for which rs_len[i] = rs_len[i'] (zero marks the end this linked list) */ int cs_head; /* is a number j of the first column of the matrix A, which has maximal number of non-zeros among other columns */ int *cs_prev; /* cs_prev[1+n]; */ /* cs_prev[0] is not used; cs_prev[j], 1 <= j <= n, is a number of the previous column of the matrix A with the same or greater number of non-zeros than in the j-th column (zero marks the end of this linked list) */ int *cs_next; /* cs_next[1+n]; */ /* cs_next[0] is not used; cs_next[j], 1 <= j <= n, is a number of the next column of the matrix A with the same or lesser number of non-zeros than in the j-th column (zero marks the end of this linked list) */ int i, j, ii, jj, k1, k2, len, t, size = 0; int *head, *rn_inv, *cn_inv; if (!(m > 0 && n > 0)) fault("triang: m = %d; n = %d; invalid dimension", m, n); /* allocate working arrays */ ndx = ucalloc(1+(m >= n ? m : n), sizeof(int)); rs_len = ucalloc(1+m, sizeof(int)); rs_head = ucalloc(1+n, sizeof(int)); rs_prev = ucalloc(1+m, sizeof(int)); rs_next = ucalloc(1+m, sizeof(int)); cs_prev = ucalloc(1+n, sizeof(int)); cs_next = ucalloc(1+n, sizeof(int)); /* build linked lists of columns of the matrix A with the same number of non-zeros */ head = rs_len; /* currently rs_len is used as working array */ for (len = 0; len <= m; len ++) head[len] = 0; for (j = 1; j <= n; j++) { /* obtain length of the j-th column */ len = mat(info, -j, ndx); insist(0 <= len && len <= m); /* include the j-th column in the corresponding linked list */ cs_prev[j] = head[len]; head[len] = j; } /* merge all linked lists of columns in one linked list, where columns are ordered by descending of their lengths */ cs_head = 0; for (len = 0; len <= m; len++) { for (j = head[len]; j != 0; j = cs_prev[j]) { cs_next[j] = cs_head; cs_head = j; } } jj = 0; for (j = cs_head; j != 0; j = cs_next[j]) { cs_prev[j] = jj; jj = j; } /* build initial doubly linked lists of rows of the matrix A with the same number of non-zeros */ for (len = 0; len <= n; len++) rs_head[len] = 0; for (i = 1; i <= m; i++) { /* obtain length of the i-th row */ rs_len[i] = len = mat(info, +i, ndx); insist(0 <= len && len <= n); /* include the i-th row in the correspondng linked list */ rs_prev[i] = 0; rs_next[i] = rs_head[len]; if (rs_next[i] != 0) rs_prev[rs_next[i]] = i; rs_head[len] = i; } /* initially all rows and columns of the matrix A are active */ for (i = 1; i <= m; i++) rn[i] = 0; for (j = 1; j <= n; j++) cn[j] = 0; /* set initial bounds of the active submatrix */ k1 = 1, k2 = n; /* main loop starts here */ while (k1 <= k2) { i = rs_head[1]; if (i != 0) { /* the i-th row of the matrix A is a row singleton, since it has the only non-zero in the active submatrix */ insist(rs_len[i] == 1); /* determine the number j of an active column of the matrix A, in which this non-zero is placed */ j = 0; t = mat(info, +i, ndx); insist(0 <= t && t <= n); for (t = t; t >= 1; t--) { jj = ndx[t]; insist(1 <= jj && jj <= n); if (cn[jj] == 0) { insist(j == 0); j = jj; } } insist(j != 0); /* the singleton is a[i,j]; move a[i,j] to the position b[k1,k1] of the matrix B */ rn[i] = cn[j] = k1; /* shift the left bound of the active submatrix */ k1++; /* increase the size of the lower triangular part */ size++; } else { /* the current active submatrix has no row singletons */ /* remove an active column with maximal number of non-zeros from the active submatrix */ j = cs_head; insist(j != 0); cn[j] = k2; /* shift the right bound of the active submatrix */ k2--; } /* the j-th column of the matrix A has been removed from the active submatrix */ /* remove the j-th column from the linked list */ if (cs_prev[j] == 0) cs_head = cs_next[j]; else cs_next[cs_prev[j]] = cs_next[j]; if (cs_next[j] == 0) /* nop */; else cs_prev[cs_next[j]] = cs_prev[j]; /* go through non-zeros of the j-th columns and update active lengths of the corresponding rows */ t = mat(info, -j, ndx); insist(0 <= t && t <= m); for (t = t; t >= 1; t--) { i = ndx[t]; insist(1 <= i && i <= m); /* the non-zero a[i,j] has left the active submatrix */ len = rs_len[i]; insist(len >= 1); /* remove the i-th row from the linked list of rows with active length len */ if (rs_prev[i] == 0) rs_head[len] = rs_next[i]; else rs_next[rs_prev[i]] = rs_next[i]; if (rs_next[i] == 0) /* nop */; else rs_prev[rs_next[i]] = rs_prev[i]; /* decrease the active length of the i-th row */ rs_len[i] = --len; /* return the i-th row to the corresponding linked list */ rs_prev[i] = 0; rs_next[i] = rs_head[len]; if (rs_next[i] != 0) rs_prev[rs_next[i]] = i; rs_head[len] = i; } } /* other rows of the matrix A, which are still active, correspond to rows k1, ..., m of the matrix B (in arbitrary order) */ for (i = 1; i <= m; i++) if (rn[i] == 0) rn[i] = k1++; /* but for columns this is not needed, because now the submatrix B2 has no columns */ for (j = 1; j <= n; j++) insist(cn[j] != 0); /* perform some optional checks */ /* make sure that rn is a permutation of {1, ..., m} and cn is a permutation of {1, ..., n} */ rn_inv = rs_len; /* used as working array */ for (ii = 1; ii <= m; ii++) rn_inv[ii] = 0; for (i = 1; i <= m; i++) { ii = rn[i]; insist(1 <= ii && ii <= m); insist(rn_inv[ii] == 0); rn_inv[ii] = i; } cn_inv = rs_head; /* used as working array */ for (jj = 1; jj <= n; jj++) cn_inv[jj] = 0; for (j = 1; j <= n; j++) { jj = cn[j]; insist(1 <= jj && jj <= n); insist(cn_inv[jj] == 0); cn_inv[jj] = j; } /* make sure that the matrix B = P*A*Q really has the form, which was declared */ for (ii = 1; ii <= size; ii++) { int diag = 0; i = rn_inv[ii]; t = mat(info, +i, ndx); insist(0 <= t && t <= n); for (t = t; t >= 1; t--) { j = ndx[t]; insist(1 <= j && j <= n); jj = cn[j]; if (jj <= size) insist(jj <= ii); if (jj == ii) { insist(!diag); diag = 1; } } insist(diag); } /* free working arrays */ ufree(ndx); ufree(rs_len); ufree(rs_head); ufree(rs_prev); ufree(rs_next); ufree(cs_prev); ufree(cs_next); /* return to the calling program */ return size; }
MDV_chunk_header_t *RfCreateMdvElevationsChunk(vol_file_handle_t *v_handle, void **data, char *calling_routine) { char calling_sequence[MAX_SEQ]; MDV_chunk_header_t *chunk_hdr = NULL; si32 *chunk_data; /* * set up calling sequence */ sprintf(calling_sequence, "%s:%s", calling_routine, THIS_ROUTINE); /* * If the Dobson object doesn't contain any elevation information, * return NULL. */ if (v_handle->vol_params->radar.nelevations <= 0) return(NULL); /* * Allocate space for the chunk header */ chunk_hdr = (MDV_chunk_header_t *)ucalloc(1, sizeof(MDV_chunk_header_t)); /* * Fill in the header parameters */ chunk_hdr->record_len1 = sizeof(MDV_chunk_header_t) - (2 * sizeof(si32)); chunk_hdr->struct_id = MDV_CHUNK_HEAD_MAGIC_COOKIE; chunk_hdr->chunk_id = MDV_CHUNK_DOBSON_ELEVATIONS; chunk_hdr->chunk_data_offset = 0; chunk_hdr->size = v_handle->vol_params->radar.nelevations * sizeof(si32); strncpy((char *)chunk_hdr->info, DOBSON_CHUNK_ELEVATIONS_INFO, MDV_CHUNK_INFO_LEN); chunk_hdr->info[MDV_CHUNK_INFO_LEN-1] = '\0'; chunk_hdr->record_len2 = chunk_hdr->record_len1; /* * Copy the data for the chunk */ chunk_data = (si32 *)umalloc(v_handle->vol_params->radar.nelevations * sizeof(si32)); memcpy((char *)chunk_data, (char *)v_handle->radar_elevations, chunk_hdr->size); *data = (void *)chunk_data; return(chunk_hdr); }
MDV_field_header_t *RfCreateMdvFieldHdr(vol_file_handle_t *v_handle, int field_num, char *calling_routine) { char calling_sequence[MAX_SEQ]; MDV_field_header_t *field_hdr = NULL; int i; /* * set up calling sequence */ sprintf(calling_sequence, "%s:%s", calling_routine, THIS_ROUTINE); /* * Allocate space for the field header */ field_hdr = (MDV_field_header_t *)ucalloc(1, sizeof(MDV_field_header_t)); /* * Fill in the fields */ field_hdr->record_len1 = sizeof(MDV_field_header_t) - (2 * sizeof(si32)); field_hdr->struct_id = MDV_FIELD_HEAD_MAGIC_COOKIE; field_hdr->field_code = 0; field_hdr->forecast_delta = 0; field_hdr->forecast_time = Rfrtime2utime(&v_handle->vol_params->mid_time); field_hdr->nx = v_handle->vol_params->cart.nx; field_hdr->ny = v_handle->vol_params->cart.ny; field_hdr->nz = v_handle->vol_params->cart.nz; if (strstr(v_handle->vol_params->cart.unitsy, "deg")) { field_hdr->proj_type = MDV_PROJ_POLAR_RADAR; } else { if (v_handle->vol_params->cart.scalex != v_handle->vol_params->cart.km_scalex) { field_hdr->proj_type = MDV_PROJ_LATLON; } else { field_hdr->proj_type = MDV_PROJ_FLAT; } } field_hdr->encoding_type = MDV_INT8; field_hdr->data_element_nbytes = 1; field_hdr->field_data_offset = 0; field_hdr->volume_size = field_hdr->nx * field_hdr->ny * field_hdr->nz * sizeof(ui08); field_hdr->proj_origin_lat = UNSCALE_INT(v_handle->vol_params->cart.latitude, 1000000); field_hdr->proj_origin_lon = UNSCALE_INT(v_handle->vol_params->cart.longitude, 1000000); for (i = 0; i < MDV_MAX_PROJ_PARAMS; i++) field_hdr->proj_param[i] = 0.0; field_hdr->vert_reference = 0.0; field_hdr->grid_dx = UNSCALE_INT(v_handle->vol_params->cart.dx, v_handle->vol_params->cart.scalex); field_hdr->grid_dy = UNSCALE_INT(v_handle->vol_params->cart.dy, v_handle->vol_params->cart.scaley); if (v_handle->vol_params->cart.dz == -1) field_hdr->grid_dz = -1; else field_hdr->grid_dz = UNSCALE_INT(v_handle->vol_params->cart.dz, v_handle->vol_params->cart.scalez); field_hdr->grid_minx = UNSCALE_INT(v_handle->vol_params->cart.minx, v_handle->vol_params->cart.scalex); field_hdr->grid_miny = UNSCALE_INT(v_handle->vol_params->cart.miny, v_handle->vol_params->cart.scaley); if (v_handle->vol_params->cart.minz == -1) field_hdr->grid_minz = -1; else field_hdr->grid_minz = UNSCALE_INT(v_handle->vol_params->cart.minz, v_handle->vol_params->cart.scalez); field_hdr->scale = UNSCALE_INT(v_handle->field_params[field_num]->scale, v_handle->field_params[field_num]->factor); field_hdr->bias = UNSCALE_INT(v_handle->field_params[field_num]->bias, v_handle->field_params[field_num]->factor); field_hdr->bad_data_value = 0; field_hdr->missing_data_value = v_handle->field_params[field_num]->missing_val; field_hdr->proj_rotation = UNSCALE_INT(v_handle->vol_params->cart.rotation, 1000000); strncpy((char *)field_hdr->field_name_long, v_handle->field_params[field_num]->name, MDV_LONG_FIELD_LEN); field_hdr->field_name_long[MDV_LONG_FIELD_LEN-1] = '\0'; strncpy((char *)field_hdr->field_name, v_handle->field_params[field_num]->name, MDV_SHORT_FIELD_LEN); field_hdr->field_name[MDV_SHORT_FIELD_LEN-1] = '\0'; strncpy((char *)field_hdr->units, v_handle->field_params[field_num]->units, MDV_UNITS_LEN); field_hdr->units[MDV_UNITS_LEN-1] = '\0'; strncpy((char *)field_hdr->transform, v_handle->field_params[field_num]->transform, MDV_TRANSFORM_LEN); field_hdr->transform[MDV_TRANSFORM_LEN-1] = '\0'; field_hdr->record_len2 = field_hdr->record_len1; return(field_hdr); }
static void gen_gomory_cut(LPX *prob, int maxlen) { int m = lpx_get_num_rows(prob); int n = lpx_get_num_cols(prob); int i, j, k, len, cut_j, *ind; double x, d, r, temp, cut_d, cut_r, *val, *work; insist(lpx_get_status(prob) == LPX_OPT); /* allocate working arrays */ ind = ucalloc(1+n, sizeof(int)); val = ucalloc(1+n, sizeof(double)); work = ucalloc(1+m+n, sizeof(double)); /* nothing is chosen so far */ cut_j = 0; cut_d = 0.0; cut_r = 0.0; /* look through all structural variables */ for (j = 1; j <= n; j++) { /* if the variable is continuous, skip it */ if (lpx_get_col_kind(prob, j) != LPX_IV) continue; /* if the variable is non-basic, skip it */ if (lpx_get_col_stat(prob, j) != LPX_BS) continue; /* if the variable is fixed, skip it */ if (lpx_get_col_type(prob, j) == LPX_FX) continue; /* obtain current primal value of the variable */ x = lpx_get_col_prim(prob, j); /* if the value is close enough to nearest integer, skip the variable */ if (fabs(x - floor(x + 0.5)) < 1e-4) continue; /* compute the row of the simplex table corresponding to the variable */ len = lpx_eval_tab_row(prob, m+j, ind, val); len = lpx_remove_tiny(len, ind, NULL, val, 1e-10); /* generate Gomory's mixed integer cut: a[1]*x[1] + ... + a[n]*x[n] >= b */ len = lpx_gomory_cut(prob, len, ind, val, work); if (len < 0) continue; insist(0 <= len && len <= n); len = lpx_remove_tiny(len, ind, NULL, val, 1e-10); if (fabs(val[0]) < 1e-10) val[0] = 0.0; /* if the cut is too long, skip it */ if (len > maxlen) continue; /* if the cut contains coefficients with too large magnitude, do not use it to prevent numeric instability */ for (k = 0; k <= len; k++) /* including rhs */ if (fabs(val[k]) > 1e+6) break; if (k <= len) continue; /* at the current point the cut inequality is violated, i.e. the residual b - (a[1]*x[1] + ... + a[n]*x[n]) > 0; note that for Gomory's cut the residual is less than 1.0 */ /* in order not to depend on the magnitude of coefficients we use scaled residual: r = [b - (a[1]*x[1] + ... + a[n]*x[n])] / max(1, |a[j]|) */ temp = 1.0; for (k = 1; k <= len; k++) if (temp < fabs(val[k])) temp = fabs(val[k]); r = (val[0] - lpx_eval_row(prob, len, ind, val)) / temp; if (r < 1e-5) continue; /* estimate degradation (worsening) of the objective function by one dual simplex step if the cut row would be introduced in the problem */ d = lpx_eval_degrad(prob, len, ind, val, LPX_LO, val[0]); /* ignore the sign of degradation */ d = fabs(d); /* which cut should be used? there are two basic cases: 1) if the degradation is non-zero, we are interested in a cut providing maximal degradation; 2) if the degradation is zero (i.e. a non-basic variable which would enter the basis in the adjacent vertex has zero reduced cost), we are interested in a cut providing maximal scaled residual; in both cases it is desired that the cut length (the number of inequality coefficients) is possibly short */ /* if both degradation and scaled residual are small, skip the cut */ if (d < 0.001 && r < 0.001) continue; /* if there is no cut chosen, choose this cut */ else if (cut_j == 0) ; /* if this cut provides stronger degradation and has shorter length, choose it */ else if (cut_d != 0.0 && cut_d < d) ; /* if this cut provides larger scaled residual and has shorter length, choose it */ else if (cut_d == 0.0 && cut_r < r) ; /* otherwise skip the cut */ else continue; /* save attributes of the cut choosen */ cut_j = j, cut_r = r, cut_d = d; } /* if a cut has been chosen, include it to the problem */ if (cut_j != 0) { j = cut_j; /* compute the row of the simplex table */ len = lpx_eval_tab_row(prob, m+j, ind, val); len = lpx_remove_tiny(len, ind, NULL, val, 1e-10); /* generate the cut */ len = lpx_gomory_cut(prob, len, ind, val, work); insist(0 <= len && len <= n); len = lpx_remove_tiny(len, ind, NULL, val, 1e-10); if (fabs(val[0]) < 1e-10) val[0] = 0.0; /* include the corresponding row in the problem */ i = lpx_add_rows(prob, 1); lpx_set_row_bnds(prob, i, LPX_LO, val[0], 0.0); lpx_set_mat_row(prob, i, len, ind, val); } /* free working arrays */ ufree(ind); ufree(val); ufree(work); return; }
int lpx_intopt(LPX *_mip) { IPP *ipp = NULL; LPX *orig = _mip, *prob = NULL; int orig_m, orig_n, i, j, ret, i_stat; /* the problem must be of MIP class */ if (lpx_get_class(orig) != LPX_MIP) { print("lpx_intopt: problem is not of MIP class"); ret = LPX_E_FAULT; goto done; } /* the problem must have at least one row and one column */ orig_m = lpx_get_num_rows(orig); orig_n = lpx_get_num_cols(orig); if (!(orig_m > 0 && orig_n > 0)) { print("lpx_intopt: problem has no rows/columns"); ret = LPX_E_FAULT; goto done; } /* check that each double-bounded row and column has bounds */ for (i = 1; i <= orig_m; i++) { if (lpx_get_row_type(orig, i) == LPX_DB) { if (lpx_get_row_lb(orig, i) >= lpx_get_row_ub(orig, i)) { print("lpx_intopt: row %d has incorrect bounds", i); ret = LPX_E_FAULT; goto done; } } } for (j = 1; j <= orig_n; j++) { if (lpx_get_col_type(orig, j) == LPX_DB) { if (lpx_get_col_lb(orig, j) >= lpx_get_col_ub(orig, j)) { print("lpx_intopt: column %d has incorrect bounds", j); ret = LPX_E_FAULT; goto done; } } } /* bounds of all integer variables must be integral */ for (j = 1; j <= orig_n; j++) { int type; double lb, ub; if (lpx_get_col_kind(orig, j) != LPX_IV) continue; type = lpx_get_col_type(orig, j); if (type == LPX_LO || type == LPX_DB || type == LPX_FX) { lb = lpx_get_col_lb(orig, j); if (lb != floor(lb)) { print("lpx_intopt: integer column %d has non-integer low" "er bound or fixed value %g", j, lb); ret = LPX_E_FAULT; goto done; } } if (type == LPX_UP || type == LPX_DB) { ub = lpx_get_col_ub(orig, j); if (ub != floor(ub)) { print("lpx_intopt: integer column %d has non-integer upp" "er bound %g", j, ub); ret = LPX_E_FAULT; goto done; } } } /* reset the status of MIP solution */ lpx_put_mip_soln(orig, LPX_I_UNDEF, NULL, NULL); /* create MIP presolver workspace */ ipp = ipp_create_wksp(); /* load the original problem into the presolver workspace */ ipp_load_orig(ipp, orig); /* perform basic MIP presolve analysis */ switch (ipp_basic_tech(ipp)) { case 0: /* no infeasibility is detected */ break; case 1: nopfs: /* primal infeasibility is detected */ print("PROBLEM HAS NO PRIMAL FEASIBLE SOLUTION"); ret = LPX_E_NOPFS; goto done; case 2: /* dual infeasibility is detected */ nodfs: print("LP RELAXATION HAS NO DUAL FEASIBLE SOLUTION"); ret = LPX_E_NODFS; goto done; default: insist(ipp != ipp); } /* reduce column bounds */ switch (ipp_reduce_bnds(ipp)) { case 0: break; case 1: goto nopfs; default: insist(ipp != ipp); } /* perform basic MIP presolve analysis */ switch (ipp_basic_tech(ipp)) { case 0: break; case 1: goto nopfs; case 2: goto nodfs; default: insist(ipp != ipp); } /* replace general integer variables by sum of binary variables, if required */ if (lpx_get_int_parm(orig, LPX_K_BINARIZE)) ipp_binarize(ipp); /* perform coefficient reduction */ ipp_reduction(ipp); /* if the resultant problem is empty, it has an empty solution, which is optimal */ if (ipp->row_ptr == NULL || ipp->col_ptr == NULL) { insist(ipp->row_ptr == NULL); insist(ipp->col_ptr == NULL); print("Objective value = %.10g", ipp->orig_dir == LPX_MIN ? +ipp->c0 : -ipp->c0); print("INTEGER OPTIMAL SOLUTION FOUND BY MIP PRESOLVER"); /* allocate recovered solution segment */ ipp->col_stat = ucalloc(1+ipp->ncols, sizeof(int)); ipp->col_mipx = ucalloc(1+ipp->ncols, sizeof(double)); for (j = 1; j <= ipp->ncols; j++) ipp->col_stat[j] = 0; /* perform MIP postsolve processing */ ipp_postsolve(ipp); /* unload recovered MIP solution and store it in the original problem object */ ipp_unload_sol(ipp, orig, LPX_I_OPT); ret = LPX_E_OK; goto done; } /* build resultant MIP problem object */ prob = ipp_build_prob(ipp); /* display some statistics */ { int m = lpx_get_num_rows(prob); int n = lpx_get_num_cols(prob); int nnz = lpx_get_num_nz(prob); int ni = lpx_get_num_int(prob); int nb = lpx_get_num_bin(prob); char s[50]; print("lpx_intopt: presolved MIP has %d row%s, %d column%s, %d" " non-zero%s", m, m == 1 ? "" : "s", n, n == 1 ? "" : "s", nnz, nnz == 1 ? "" : "s"); if (nb == 0) strcpy(s, "none of"); else if (ni == 1 && nb == 1) strcpy(s, ""); else if (nb == 1) strcpy(s, "one of"); else if (nb == ni) strcpy(s, "all of"); else sprintf(s, "%d of", nb); print("lpx_intopt: %d integer column%s, %s which %s binary", ni, ni == 1 ? "" : "s", s, nb == 1 ? "is" : "are"); } /* inherit some control parameters and statistics */ lpx_set_int_parm(prob, LPX_K_PRICE, lpx_get_int_parm(orig, LPX_K_PRICE)); lpx_set_real_parm(prob, LPX_K_RELAX, lpx_get_real_parm(orig, LPX_K_RELAX)); lpx_set_real_parm(prob, LPX_K_TOLBND, lpx_get_real_parm(orig, LPX_K_TOLBND)); lpx_set_real_parm(prob, LPX_K_TOLDJ, lpx_get_real_parm(orig, LPX_K_TOLDJ)); lpx_set_real_parm(prob, LPX_K_TOLPIV, lpx_get_real_parm(orig, LPX_K_TOLPIV)); lpx_set_int_parm(prob, LPX_K_ITLIM, lpx_get_int_parm(orig, LPX_K_ITLIM)); lpx_set_int_parm(prob, LPX_K_ITCNT, lpx_get_int_parm(orig, LPX_K_ITCNT)); lpx_set_real_parm(prob, LPX_K_TMLIM, lpx_get_real_parm(orig, LPX_K_TMLIM)); lpx_set_int_parm(prob, LPX_K_BRANCH, lpx_get_int_parm(orig, LPX_K_BRANCH)); lpx_set_int_parm(prob, LPX_K_BTRACK, lpx_get_int_parm(orig, LPX_K_BTRACK)); lpx_set_real_parm(prob, LPX_K_TOLINT, lpx_get_real_parm(orig, LPX_K_TOLINT)); lpx_set_real_parm(prob, LPX_K_TOLOBJ, lpx_get_real_parm(orig, LPX_K_TOLOBJ)); /* build an advanced initial basis */ lpx_adv_basis(prob); /* solve LP relaxation */ print("Solving LP relaxation..."); switch (lpx_simplex(prob)) { case LPX_E_OK: break; case LPX_E_ITLIM: ret = LPX_E_ITLIM; goto done; case LPX_E_TMLIM: ret = LPX_E_TMLIM; goto done; default: print("lpx_intopt: cannot solve LP relaxation"); ret = LPX_E_SING; goto done; } /* analyze status of the basic solution */ switch (lpx_get_status(prob)) { case LPX_OPT: break; case LPX_NOFEAS: ret = LPX_E_NOPFS; goto done; case LPX_UNBND: ret = LPX_E_NODFS; goto done; default: insist(prob != prob); } /* generate cutting planes, if necessary */ if (lpx_get_int_parm(orig, LPX_K_USECUTS)) { ret = generate_cuts(prob); if (ret != LPX_E_OK) goto done; } /* call the branch-and-bound solver */ ret = lpx_integer(prob); /* determine status of MIP solution */ i_stat = lpx_mip_status(prob); if (i_stat == LPX_I_OPT || i_stat == LPX_I_FEAS) { /* load MIP solution of the resultant problem into presolver workspace */ ipp_load_sol(ipp, prob); /* perform MIP postsolve processing */ ipp_postsolve(ipp); /* unload recovered MIP solution and store it in the original problem object */ ipp_unload_sol(ipp, orig, i_stat); } else { /* just set the status of MIP solution */ lpx_put_mip_soln(orig, i_stat, NULL, NULL); } done: /* copy back statistics about spent resources */ if (prob != NULL) { lpx_set_int_parm(orig, LPX_K_ITLIM, lpx_get_int_parm(prob, LPX_K_ITLIM)); lpx_set_int_parm(orig, LPX_K_ITCNT, lpx_get_int_parm(prob, LPX_K_ITCNT)); lpx_set_real_parm(orig, LPX_K_TMLIM, lpx_get_real_parm(prob, LPX_K_TMLIM)); } /* delete the resultant problem object */ if (prob != NULL) lpx_delete_prob(prob); /* delete MIP presolver workspace */ if (ipp != NULL) ipp_delete_wksp(ipp); return ret; }
int lpx_print_sens_bnds(LPX *lp, char *fname) { FILE *fp = NULL; int what, round; print("lpx_print_sens_bnds: writing LP problem solution bounds to" " `%s'...", fname); #if 1 /* added by mao */ /* this routine needs factorization of the current basis matrix which, however, does not exist if the basic solution was obtained by the lp presolver; therefore we should warm up the basis to be sure that the factorization is valid (note that if the factorization exists, lpx_warm_up does nothing) */ lpx_warm_up(lp); #endif #if 0 /* 21/XII-2003 by mao */ if (lp->b_stat == LPX_B_UNDEF) #else if (!lpx_is_b_avail(lp)) #endif { print("lpx_print_sens_bnds: basis information not available (m" "ay be a presolve issue)"); goto fail; } fp = ufopen(fname, "w"); if (fp == NULL) { print("lpx_print_sens_bnds: can't create `%s' - %s", fname, strerror(errno)); goto fail; } /* problem name */ { char *name; name = lpx_get_prob_name(lp); if (name == NULL) name = ""; fprintf(fp, "%-12s%s\n", "Problem:", name); } /* number of rows (auxiliary variables) */ { int nr; nr = lpx_get_num_rows(lp); fprintf(fp, "%-12s%d\n", "Rows:", nr); } /* number of columns (structural variables) */ { int nc; nc = lpx_get_num_cols(lp); fprintf(fp, "%-12s%d\n", "Columns:", nc); } /* number of non-zeros (constraint coefficients) */ { int nz; nz = lpx_get_num_nz(lp); fprintf(fp, "%-12s%d\n", "Non-zeros:", nz); } /* solution status */ { int status; status = lpx_get_status(lp); fprintf(fp, "%-12s%s\n", "Status:", status == LPX_OPT ? "OPTIMAL" : status == LPX_FEAS ? "FEASIBLE" : status == LPX_INFEAS ? "INFEASIBLE (INTERMEDIATE)" : status == LPX_NOFEAS ? "INFEASIBLE (FINAL)" : status == LPX_UNBND ? "UNBOUNDED" : status == LPX_UNDEF ? "UNDEFINED" : "???"); } /* explanation/warning */ { fprintf(fp, "\nExplanation: This file presents amounts by whi" "ch objective coefficients,\n"); fprintf(fp, "constraint bounds, and variable bounds may be cha" "nged in the original problem\n"); fprintf(fp, "while the optimal basis remains the same. Note t" "hat the optimal solution\n"); fprintf(fp, "and objective value may change even though the ba" "sis remains the same.\n"); fprintf(fp, "These bounds assume that all parameters remain fi" "xed except the one in\n"); fprintf(fp, "question. If more than one parameter is changed," " it is possible for the\n"); fprintf(fp, "optimal basis to change even though each paramete" "r stays within its bounds.\n"); fprintf(fp, "For more details, consult a text on linear progra" "mming.\n"); } /* Sensitivity ranges if solution was optimal */ { int status; status = lpx_get_status(lp); if (status == LPX_OPT) { int i,j,k,m,n; int dir; double max_inc, max_dec; int *index; double *val; fprintf(fp, "\nObjective Coefficient Analysis\n"); fprintf(fp, " No. Column name St Value Max incr" "ease Max decrease\n"); fprintf(fp, "------ ------------ -- ------------- ---------" "---- ------------- \n"); n = lpx_get_num_cols(lp); m = lpx_get_num_rows(lp); dir = lpx_get_obj_dir(lp); /* allocate memory for index and val arrays */ index = ucalloc(1+n+m, sizeof(int)); val = ucalloc(1+n+m, sizeof(double)); for (j = 1; j <= n; j++) { char *name; int typx, tagx; double lb, ub, vx, dx; name = lpx_get_col_name(lp, j); if (name == NULL) name = ""; lpx_get_col_bnds(lp, j, &typx, &lb, &ub); #if 0 /* 21/XII-2003 by mao */ round = lp->round, lp->round = 1; lpx_get_col_info(lp, j, &tagx, &vx, &dx); lp->round = round; #else round = lpx_get_int_parm(lp, LPX_K_ROUND); lpx_set_int_parm(lp, LPX_K_ROUND, 1); lpx_get_col_info(lp, j, &tagx, &vx, &dx); lpx_set_int_parm(lp, LPX_K_ROUND, round); #endif /* row/column ordinal number */ fprintf(fp, "%6d ", j); /* row column/name */ if (strlen(name) <= 12) fprintf(fp, "%-12s ", name); else fprintf(fp, "%s\n%20s", name, ""); /* row/column status */ fprintf(fp, "%s ", tagx == LPX_BS ? "B " : tagx == LPX_NL ? "NL" : tagx == LPX_NU ? "NU" : tagx == LPX_NF ? "NF" : tagx == LPX_NS ? "NS" : "??"); /* objective coefficient */ fprintf(fp, "%13.6g ", lpx_get_obj_coef(lp, j)); if (tagx == LPX_NL) { if (dir==LPX_MIN) { /* reduced cost must be positive */ max_inc = DBL_MAX; /* really represents infinity */ max_dec = dx; } else { /* reduced cost must be negative */ max_inc = -dx; max_dec = DBL_MAX; /* means infinity */ } } if (tagx == LPX_NU) { if (dir==LPX_MIN) { /* reduced cost must be negative */ max_inc = -dx; max_dec = DBL_MAX; } else { max_inc = DBL_MAX; max_dec = dx; } } if (tagx == LPX_NF) { /* can't change nonbasic free variables' cost */ max_inc = 0.0; max_dec = 0.0; } if (tagx == LPX_NS) { /* doesn't matter what happens to the cost */ max_inc = DBL_MAX; max_dec = DBL_MAX; } if (tagx == LPX_BS) { int len; /* We need to see how this objective coefficient affects reduced costs of other variables */ len = lpx_eval_tab_row(lp, m+j, index, val); max_inc = DBL_MAX; max_dec = DBL_MAX; for (i = 1; i <= len; i++) { /*int stat;*/ int tagx2; double vx2, dx2; double delta; if (index[i]>m) lpx_get_col_info(lp, index[i]-m, &tagx2, &vx2, &dx2); else lpx_get_row_info(lp, index[i], &tagx2, &vx2, &dx2); if (tagx2 == LPX_NL) { if (val[i] != 0.0) { delta = dx2 / val[i]; if (delta < 0 && -delta < max_inc) max_inc = -delta; else if (delta >0 && delta < max_dec) max_dec = delta; } } if (tagx2 == LPX_NU) { if (val[i] != 0.0) { delta = dx2 / val[i]; if (delta < 0 && -delta < max_inc) max_inc = -delta; else if (delta > 0 && delta < max_dec) max_dec = delta; } } if (tagx2 == LPX_NF) { if (val[i] != 0.0) { max_inc = 0.0; max_dec = 0.0; } } } } if (max_inc == -0.0) max_inc = 0.0; if (max_dec == -0.0) max_dec = 0.0; if (max_inc == DBL_MAX) fprintf(fp, "%13s ", "infinity"); else if (max_inc < 1.0e-12 && max_inc > 0) fprintf(fp, "%13s ", "< eps"); else fprintf(fp, "%13.6g ", max_inc); if (max_dec == DBL_MAX) fprintf(fp, "%13s ", "infinity"); else if (max_dec < 1.0e-12 && max_dec > 0) fprintf(fp, "%13s ", "< eps"); else fprintf(fp, "%13.6g ", max_dec); fprintf(fp, "\n"); } for (what = 1; what <= 2; what++) { int ij, mn; fprintf(fp, "\n"); fprintf(fp, "%s Analysis\n", what==1? "Constraint Bounds":"Variable Bounds"); fprintf(fp, " No. %12s St Value Max increase " " Max decrease\n", what==1 ? " Row name":"Column name"); fprintf(fp, "------ ------------ -- ------------- ------" "------- ------------- \n"); mn = what==1 ? m : n; for (ij = 1; ij <= mn; ij++) { char *name; int typx, tagx; double lb, ub, vx, dx; if (what==1) name = lpx_get_row_name(lp, ij); else name = lpx_get_col_name(lp, ij); if (name == NULL) name = ""; #if 0 /* 21/XII-2003 by mao */ if (what==1) { lpx_get_row_bnds(lp, ij, &typx, &lb, &ub); round = lp->round, lp->round = 1; lpx_get_row_info(lp, ij, &tagx, &vx, &dx); lp->round = round; } else { lpx_get_col_bnds(lp, ij, &typx, &lb, &ub); round = lp->round, lp->round = 1; lpx_get_col_info(lp, ij, &tagx, &vx, &dx); lp->round = round; } #else round = lpx_get_int_parm(lp, LPX_K_ROUND); lpx_set_int_parm(lp, LPX_K_ROUND, 1); if (what==1) { lpx_get_row_bnds(lp, ij, &typx, &lb, &ub); lpx_get_row_info(lp, ij, &tagx, &vx, &dx); } else { lpx_get_col_bnds(lp, ij, &typx, &lb, &ub); lpx_get_col_info(lp, ij, &tagx, &vx, &dx); } lpx_set_int_parm(lp, LPX_K_ROUND, round); #endif /* row/column ordinal number */ fprintf(fp, "%6d ", ij); /* row column/name */ if (strlen(name) <= 12) fprintf(fp, "%-12s ", name); else fprintf(fp, "%s\n%20s", name, ""); /* row/column status */ fprintf(fp, "%s ", tagx == LPX_BS ? "B " : tagx == LPX_NL ? "NL" : tagx == LPX_NU ? "NU" : tagx == LPX_NF ? "NF" : tagx == LPX_NS ? "NS" : "??"); fprintf(fp, "\n"); /* first check lower bound */ if (typx == LPX_LO || typx == LPX_DB || typx == LPX_FX) { int at_lower; at_lower = 0; if (tagx == LPX_BS || tagx == LPX_NU) { max_inc = vx - lb; max_dec = DBL_MAX; } if (tagx == LPX_NS) { max_inc = 0.0; max_dec = 0.0; if (dir == LPX_MIN && dx > 0) at_lower = 1; if (dir == LPX_MAX && dx < 0) at_lower = 1; } if (tagx == LPX_NL || at_lower == 1) { int len; /* we have to see how it affects basic variables */ len = lpx_eval_tab_col(lp, what==1?ij:ij+m, index, val); k = lpx_prim_ratio_test(lp, len, index, val, 1, 10e-7); max_inc = DBL_MAX; if (k != 0) { /*int stat;*/ int tagx2, typx2; double vx2, dx2, lb2, ub2; /*double delta;*/ double alpha; int l; for (l = 1; l <= len; l++) if (index[l] == k) alpha = val[l]; if (k>m) { lpx_get_col_info(lp, k-m, &tagx2, &vx2, &dx2); lpx_get_col_bnds(lp, k-m, &typx2, &lb2, &ub2); } else { lpx_get_row_info(lp, k, &tagx2, &vx2, &dx2); lpx_get_row_bnds(lp, k, &typx2, &lb2, &ub2); } /* Check which direction; remember this is upper bound */ if (alpha > 0) max_inc = (ub2 - vx2)/ alpha; else max_inc = (lb2 - vx2)/ alpha; } /* now check lower bound */ k = lpx_prim_ratio_test(lp, len, index, val, -1, 10e-7); max_dec = DBL_MAX; if (k != 0) { /*int stat;*/ int tagx2, typx2; double vx2, dx2, lb2, ub2; /*double delta;*/ double alpha; int l; for (l = 1; l <= len; l++) if (index[l] == k) alpha = val[l]; if (k>m) { lpx_get_col_info(lp, k-m, &tagx2, &vx2, &dx2); lpx_get_col_bnds(lp, k-m, &typx2, &lb2, &ub2); } else { lpx_get_row_info(lp, k, &tagx2, &vx2, &dx2); lpx_get_row_bnds(lp, k, &typx2, &lb2, &ub2); } /* Check which direction; remember this is lower bound */ if (alpha > 0) max_dec = (vx2 - lb2)/ alpha; else max_dec = (vx2 - ub2)/ alpha; } } /* bound */ if (typx == LPX_DB || typx == LPX_FX) { if (max_inc > ub - lb) max_inc = ub - lb; } fprintf(fp, " LOWER %13.6g ", lb); if (max_inc == -0.0) max_inc = 0.0; if (max_dec == -0.0) max_dec = 0.0; if (max_inc == DBL_MAX) fprintf(fp, "%13s ", "infinity"); else if (max_inc < 1.0e-12 && max_inc > 0) fprintf(fp, "%13s ", "< eps"); else fprintf(fp, "%13.6g ", max_inc); if (max_dec == DBL_MAX) fprintf(fp, "%13s ", "infinity"); else if (max_dec < 1.0e-12 && max_dec > 0) fprintf(fp, "%13s ", "< eps"); else fprintf(fp, "%13.6g ", max_dec); fprintf(fp, "\n"); } /* now check upper bound */ if (typx == LPX_UP || typx == LPX_DB || typx == LPX_FX) { int at_upper; at_upper = 0; if (tagx == LPX_BS || tagx == LPX_NL) { max_inc = DBL_MAX; max_dec = ub - vx; } if (tagx == LPX_NS) { max_inc = 0.0; max_dec = 0.0; if (dir == LPX_MIN && dx < 0) at_upper = 1; if (dir == LPX_MAX && dx > 0) at_upper = 1; } if (tagx == LPX_NU || at_upper == 1) { int len; /* we have to see how it affects basic variables */ len = lpx_eval_tab_col(lp, what==1?ij:ij+m, index, val); k = lpx_prim_ratio_test(lp, len, index, val, 1, 10e-7); max_inc = DBL_MAX; if (k != 0) { /*int stat;*/ int tagx2, typx2; double vx2, dx2, lb2, ub2; /*double delta;*/ double alpha; int l; for (l = 1; l <= len; l++) if (index[l] == k) alpha = val[l]; if (k>m) { lpx_get_col_info(lp, k-m, &tagx2, &vx2, &dx2); lpx_get_col_bnds(lp, k-m, &typx2, &lb2, &ub2); } else { lpx_get_row_info(lp, k, &tagx2, &vx2, &dx2); lpx_get_row_bnds(lp, k, &typx2, &lb2, &ub2); } /* Check which direction; remember this is upper bound */ if (alpha > 0) max_inc = (ub2 - vx2)/ alpha; else max_inc = (lb2 - vx2)/ alpha; } /* now check lower bound */ k = lpx_prim_ratio_test(lp, len, index, val, -1, 10e-7); max_dec = DBL_MAX; if (k != 0) { /*int stat;*/ int tagx2, typx2; double vx2, dx2, lb2, ub2; /*double delta;*/ double alpha; int l; for (l = 1; l <= len; l++) if (index[l] == k) alpha = val[l]; if (k>m) { lpx_get_col_info(lp, k-m, &tagx2, &vx2, &dx2); lpx_get_col_bnds(lp, k-m, &typx2, &lb2, &ub2); } else { lpx_get_row_info(lp, k, &tagx2, &vx2, &dx2); lpx_get_row_bnds(lp, k, &typx2, &lb2, &ub2); } /* Check which direction; remember this is lower bound */ if (alpha > 0) max_dec = (vx2 - lb2)/ alpha; else max_dec = (vx2 - ub2)/ alpha; } } if (typx == LPX_DB || typx == LPX_FX) { if (max_dec > ub - lb) max_dec = ub - lb; } /* bound */ fprintf(fp, " UPPER %13.6g ", ub); if (max_inc == -0.0) max_inc = 0.0; if (max_dec == -0.0) max_dec = 0.0; if (max_inc == DBL_MAX) fprintf(fp, "%13s ", "infinity"); else if (max_inc < 1.0e-12 && max_inc > 0) fprintf(fp, "%13s ", "< eps"); else fprintf(fp, "%13.6g ", max_inc); if (max_dec == DBL_MAX) fprintf(fp, "%13s ", "infinity"); else if (max_dec < 1.0e-12 && max_dec > 0) fprintf(fp, "%13s ", "< eps"); else fprintf(fp, "%13.6g ", max_dec); fprintf(fp, "\n"); } } } /* free the memory we used */ ufree(index); ufree(val); } else fprintf(fp, "No range information since solution is not o" "ptimal.\n"); } fprintf(fp, "\n"); fprintf(fp, "End of output\n"); fflush(fp); if (ferror(fp)) { print("lpx_print_sens_bnds: can't write to `%s' - %s", fname, strerror(errno)); goto fail; } ufclose(fp); return 0; fail: if (fp != NULL) ufclose(fp); return 1; }
void build_problem(MPL *mpl) { STATEMENT *stmt; MEMBER *memb; VARIABLE *v; CONSTRAINT *c; FORMULA *t; int i, j; insist(mpl->m == 0); insist(mpl->n == 0); insist(mpl->row == NULL); insist(mpl->col == NULL); /* check that all elemental variables has zero column numbers */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_VARIABLE) { v = stmt->u.var; for (memb = v->array->head; memb != NULL; memb = memb->next) insist(memb->value.var->j == 0); } } /* assign row numbers to elemental constraints and objectives */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_CONSTRAINT) { c = stmt->u.con; for (memb = c->array->head; memb != NULL; memb = memb->next) { insist(memb->value.con->i == 0); memb->value.con->i = ++mpl->m; /* walk through linear form and mark elemental variables, which are referenced at least once */ for (t = memb->value.con->form; t != NULL; t = t->next) { insist(t->var != NULL); t->var->memb->value.var->j = -1; } } } } /* assign column numbers to marked elemental variables */ for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_VARIABLE) { v = stmt->u.var; for (memb = v->array->head; memb != NULL; memb = memb->next) if (memb->value.var->j != 0) memb->value.var->j = ++mpl->n; } } /* build list of rows */ mpl->row = ucalloc(1+mpl->m, sizeof(ELEMCON *)); for (i = 1; i <= mpl->m; i++) mpl->row[i] = NULL; for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_CONSTRAINT) { c = stmt->u.con; for (memb = c->array->head; memb != NULL; memb = memb->next) { i = memb->value.con->i; insist(1 <= i && i <= mpl->m); insist(mpl->row[i] == NULL); mpl->row[i] = memb->value.con; } } } for (i = 1; i <= mpl->m; i++) insist(mpl->row[i] != NULL); /* build list of columns */ mpl->col = ucalloc(1+mpl->n, sizeof(ELEMVAR *)); for (j = 1; j <= mpl->n; j++) mpl->col[j] = NULL; for (stmt = mpl->model; stmt != NULL; stmt = stmt->next) { if (stmt->type == A_VARIABLE) { v = stmt->u.var; for (memb = v->array->head; memb != NULL; memb = memb->next) { j = memb->value.var->j; if (j == 0) continue; insist(1 <= j && j <= mpl->n); insist(mpl->col[j] == NULL); mpl->col[j] = memb->value.var; } } } for (j = 1; j <= mpl->n; j++) insist(mpl->col[j] != NULL); return; }
void lpx_adv_basis(LPX *lp) { /* build advanced initial basis */ int m = lpx_get_num_rows(lp); int n = lpx_get_num_cols(lp); int i, j, jj, k, size; int *rn, *cn, *rn_inv, *cn_inv; int typx, *tagx = ucalloc(1+m+n, sizeof(int)); double lb, ub; if (m == 0) fault("lpx_adv_basis: problem has no rows"); if (n == 0) fault("lpx_adv_basis: problem has no columns"); /* use the routine triang (see above) to find maximal triangular part of the augmented constraint matrix A~ = (I|-A); in order to prevent columns of fixed variables to be included in the triangular part, such columns are implictly removed from the matrix A~ by the routine adv_mat */ rn = ucalloc(1+m, sizeof(int)); cn = ucalloc(1+m+n, sizeof(int)); size = triang(m, m+n, lp, mat, rn, cn); if (lpx_get_int_parm(lp, LPX_K_MSGLEV) >= 3) print("lpx_adv_basis: size of triangular part = %d", size); /* the first size rows and columns of the matrix P*A~*Q (where P and Q are permutation matrices defined by the arrays rn and cn) form a lower triangular matrix; build the arrays (rn_inv and cn_inv), which define the matrices inv(P) and inv(Q) */ rn_inv = ucalloc(1+m, sizeof(int)); cn_inv = ucalloc(1+m+n, sizeof(int)); for (i = 1; i <= m; i++) rn_inv[rn[i]] = i; for (j = 1; j <= m+n; j++) cn_inv[cn[j]] = j; /* include the columns of the matrix A~, which correspond to the first size columns of the matrix P*A~*Q, in the basis */ for (k = 1; k <= m+n; k++) tagx[k] = -1; for (jj = 1; jj <= size; jj++) { j = cn_inv[jj]; /* the j-th column of A~ is the jj-th column of P*A~*Q */ tagx[j] = LPX_BS; } /* if size < m, we need to add appropriate columns of auxiliary variables to the basis */ for (jj = size + 1; jj <= m; jj++) { /* the jj-th column of P*A~*Q should be replaced by the column of the auxiliary variable, for which the only unity element is placed in the position [jj,jj] */ i = rn_inv[jj]; /* the jj-th row of P*A~*Q is the i-th row of A~, but in the i-th row of A~ the unity element belongs to the i-th column of A~; therefore the disired column corresponds to the i-th auxiliary variable (note that this column doesn't belong to the triangular part found by the routine triang) */ insist(1 <= i && i <= m); insist(cn[i] > size); tagx[i] = LPX_BS; } /* free working arrays */ ufree(rn); ufree(cn); ufree(rn_inv); ufree(cn_inv); /* build tags of non-basic variables */ for (k = 1; k <= m+n; k++) { if (tagx[k] != LPX_BS) { if (k <= m) lpx_get_row_bnds(lp, k, &typx, &lb, &ub); else lpx_get_col_bnds(lp, k-m, &typx, &lb, &ub); switch (typx) { case LPX_FR: tagx[k] = LPX_NF; break; case LPX_LO: tagx[k] = LPX_NL; break; case LPX_UP: tagx[k] = LPX_NU; break; case LPX_DB: tagx[k] = (fabs(lb) <= fabs(ub) ? LPX_NL : LPX_NU); break; case LPX_FX: tagx[k] = LPX_NS; break; default: insist(typx != typx); } } } for (k = 1; k <= m+n; k++) { if (k <= m) lpx_set_row_stat(lp, k, tagx[k]); else lpx_set_col_stat(lp, k-m, tagx[k]); } ufree(tagx); return; }
MPL *mpl_initialize(void) { MPL *mpl; mpl = umalloc(sizeof(MPL)); /* scanning segment */ mpl->line = 0; mpl->c = 0; mpl->token = 0; mpl->imlen = 0; mpl->image = ucalloc(MAX_LENGTH+1, sizeof(char)); mpl->image[0] = '\0'; mpl->value = 0.0; mpl->b_token = 0; mpl->b_imlen = 0; mpl->b_image = ucalloc(MAX_LENGTH+1, sizeof(char)); mpl->b_image[0] = '\0'; mpl->b_value = 0.0; mpl->f_dots = 0; mpl->f_scan = 0; mpl->f_token = 0; mpl->f_imlen = 0; mpl->f_image = ucalloc(MAX_LENGTH+1, sizeof(char)); mpl->f_image[0] = '\0'; mpl->f_value = 0.0; mpl->context = ucalloc(CONTEXT_SIZE, sizeof(char)); memset(mpl->context, ' ', CONTEXT_SIZE); mpl->c_ptr = 0; mpl->flag_d = 0; /* translating segment */ mpl->pool = dmp_create_pool(0); mpl->tree = avl_create_tree(NULL, avl_strcmp); mpl->model = NULL; mpl->flag_x = 0; mpl->as_within = 0; mpl->as_in = 0; mpl->as_binary = 0; mpl->flag_s = 0; /* common segment */ mpl->strings = dmp_create_pool(sizeof(STRING)); mpl->symbols = dmp_create_pool(sizeof(SYMBOL)); mpl->tuples = dmp_create_pool(sizeof(TUPLE)); mpl->arrays = dmp_create_pool(sizeof(ARRAY)); mpl->members = dmp_create_pool(sizeof(MEMBER)); mpl->elemvars = dmp_create_pool(sizeof(ELEMVAR)); mpl->formulae = dmp_create_pool(sizeof(FORMULA)); mpl->elemcons = dmp_create_pool(sizeof(ELEMCON)); mpl->a_list = NULL; mpl->sym_buf = ucalloc(255+1, sizeof(char)); mpl->sym_buf[0] = '\0'; mpl->tup_buf = ucalloc(255+1, sizeof(char)); mpl->tup_buf[0] = '\0'; /* generating/postsolving segment */ mpl->rand = rng_create_rand(); mpl->flag_p = 0; mpl->stmt = NULL; mpl->m = 0; mpl->n = 0; mpl->row = NULL; mpl->col = NULL; /* input/output segment */ mpl->in_fp = NULL; mpl->in_file = NULL; mpl->out_fp = NULL; mpl->out_file = NULL; mpl->out_buf = NULL; mpl->out_cnt = 0; /* solver interface segment */ if (setjmp(mpl->jump)) insist(mpl != mpl); mpl->phase = 0; mpl->mod_file = NULL; mpl->mpl_buf = ucalloc(255+1, sizeof(char)); mpl->mpl_buf[0] = '\0'; return mpl; }
static void store_mult_spdb(date_time_t *ptime, double lat, double lon, double alt, char *callsign) { static int first_call = TRUE; char db_path[MAX_PATH_LEN]; int i, index; ac_posn_t posn; if (first_call) { Db_array = (spdb_handle_t *) ucalloc (Glob->params.callsigns.len, sizeof(spdb_handle_t)); for (i = 0; i < Glob->params.callsigns.len; i++) { sprintf(db_path, "%s%s%s", Glob->params.db_dir, PATH_DELIM, Glob->params.callsigns.val[i]); if (SPDB_init(&Db_array[i], AC_POSN_PROD_LABEL, AC_POSN_PROD_CODE, db_path)) { fprintf(stderr, "WARNING %s:store_mult_spdb\n", Glob->prog_name); fprintf(stderr, "Cannot open ac_posn data base %s\n", db_path); tidy_and_exit(-1); } } /* i */ first_call = FALSE; } /* first_call */ /* * get database index */ index = ac_index(callsign); if (index < 0) { fprintf(stderr, "WARNING %s:store_mult_spdb\n", Glob->prog_name); fprintf(stderr, "Ac callsign %s not recognized\n", callsign); return; } posn.lat = lat; posn.lon = lon; posn.alt = alt; STRncopy(posn.callsign, callsign, AC_POSN_N_CALLSIGN); /* * set to bigend format */ BE_from_ac_posn(&posn); /* * store in data base */ if (SPDB_store_over(&Db_array[index], 0, ptime->unix_time, ptime->unix_time + Glob->params.valid_period, (void *) &posn, sizeof(ac_posn_t))) { fprintf(stderr, "WARNING %s:store_mult_spdb\n", Glob->prog_name); fprintf(stderr, "Could not store posn for ac callsign %s\n", callsign); } return; }
int spx_dual_opt(SPX *spx) { /* find optimal solution (dual simplex) */ int m = spx->m; int n = spx->n; int ret; double start = utime(), spent = 0.0, obj; /* the initial basis should be "warmed up" */ if (spx->b_stat != LPX_B_VALID || spx->p_stat == LPX_P_UNDEF || spx->d_stat == LPX_D_UNDEF) { ret = LPX_E_BADB; goto done; } /* the initial basic solution should be dual feasible */ if (spx->d_stat != LPX_D_FEAS) { ret = LPX_E_INFEAS; goto done; } /* if the initial basic solution is primal feasible, nothing to search for */ if (spx->p_stat == LPX_P_FEAS) { ret = LPX_E_OK; goto done; } /* allocate the working segment */ insist(spx->meth == 0); spx->meth = 'D'; spx->p = 0; spx->p_tag = 0; spx->q = 0; spx->zeta = ucalloc(1+m, sizeof(double)); spx->ap = ucalloc(1+n, sizeof(double)); spx->aq = ucalloc(1+m, sizeof(double)); spx->gvec = NULL; spx->dvec = ucalloc(1+m, sizeof(double)); spx->refsp = (spx->price ? ucalloc(1+m+n, sizeof(int)) : NULL); spx->count = 0; spx->work = ucalloc(1+m+n, sizeof(double)); spx->orig_typx = NULL; spx->orig_lb = spx->orig_ub = NULL; spx->orig_dir = 0; spx->orig_coef = NULL; beg: /* compute initial value of the objective function */ obj = spx_eval_obj(spx); /* initialize weights of basic variables */ if (!spx->price) { /* textbook pricing will be used */ int i; for (i = 1; i <= m; i++) spx->dvec[i] = 1.0; } else { /* steepest edge pricing will be used */ spx_reset_refsp(spx); } /* display information about the initial basic solution */ if (spx->msg_lev >= 2 && spx->it_cnt % spx->out_frq != 0 && spx->out_dly <= spent) dual_opt_dpy(spx); /* main loop starts here */ for (;;) { /* determine the spent amount of time */ spent = utime() - start; /* display information about the current basic solution */ if (spx->msg_lev >= 2 && spx->it_cnt % spx->out_frq == 0 && spx->out_dly <= spent) dual_opt_dpy(spx); /* if the objective function should be minimized, check if it has reached its upper bound */ if (spx->dir == LPX_MIN && obj >= spx->obj_ul) { ret = LPX_E_OBJUL; break; } /* if the objective function should be maximized, check if it has reached its lower bound */ if (spx->dir == LPX_MAX && obj <= spx->obj_ll) { ret = LPX_E_OBJLL; break; } /* check if the iterations limit has been exhausted */ if (spx->it_lim == 0) { ret = LPX_E_ITLIM; break; } /* check if the time limit has been exhausted */ if (spx->tm_lim >= 0.0 && spx->tm_lim <= spent) { ret = LPX_E_TMLIM; break; } /* choose basic variable */ spx_dual_chuzr(spx, spx->tol_bnd); /* if no xB[p] has been chosen, the current basic solution is primal feasible and therefore optimal */ if (spx->p == 0) { ret = LPX_E_OK; break; } /* compute the p-th row of the inverse inv(B) */ spx_eval_rho(spx, spx->p, spx->zeta); /* compute the p-th row of the current simplex table */ spx_eval_row(spx, spx->zeta, spx->ap); /* choose non-basic variable xN[q] */ if (spx_dual_chuzc(spx, spx->relax * spx->tol_dj)) { /* the basis matrix should be reinverted, because the p-th row of the simplex table is unreliable */ insist("not implemented yet" == NULL); } /* if no xN[q] has been chosen, there is no primal feasible solution (the dual problem has unbounded solution) */ if (spx->q == 0) { ret = LPX_E_NOFEAS; break; } /* compute the q-th column of the current simplex table (later this column will enter the basis) */ spx_eval_col(spx, spx->q, spx->aq, 1); /* update values of basic variables and value of the objective function */ spx_update_bbar(spx, &obj); /* update simplex multipliers */ spx_update_pi(spx); /* update reduced costs of non-basic variables */ spx_update_cbar(spx, 0); /* update weights of basic variables */ if (spx->price) spx_update_dvec(spx); /* if xB[p] is fixed variable, adjust its non-basic tag */ if (spx->typx[spx->indx[spx->p]] == LPX_FX) spx->p_tag = LPX_NS; /* jump to the adjacent vertex of the LP polyhedron */ if (spx_change_basis(spx)) { /* the basis matrix should be reinverted */ if (spx_invert(spx) != 0) { /* numerical problems with the basis matrix */ spx->p_stat = LPX_P_UNDEF; spx->d_stat = LPX_D_UNDEF; ret = LPX_E_SING; goto done; } /* compute the current basic solution components */ spx_eval_bbar(spx); obj = spx_eval_obj(spx); spx_eval_pi(spx); spx_eval_cbar(spx); /* check dual feasibility */ if (spx_check_cbar(spx, spx->tol_dj) != 0.0) { /* the current solution became dual infeasible due to round-off errors */ ret = LPX_E_INSTAB; break; } } #if 0 /* check accuracy of main solution components after updating (for debugging purposes only) */ { double ae_bbar = spx_err_in_bbar(spx); double ae_pi = spx_err_in_pi(spx); double ae_cbar = spx_err_in_cbar(spx, 0); double ae_dvec = spx->price ? spx_err_in_dvec(spx) : 0.0; print("bbar: %g; pi: %g; cbar: %g; dvec: %g", ae_bbar, ae_pi, ae_cbar, ae_dvec); if (ae_bbar > 1e-9 || ae_pi > 1e-9 || ae_cbar > 1e-9 || ae_dvec > 1e-3) insist("solution accuracy too low" == NULL); } #endif } /* compute the final basic solution components */ spx_eval_bbar(spx); obj = spx_eval_obj(spx); spx_eval_pi(spx); spx_eval_cbar(spx); if (spx_check_bbar(spx, spx->tol_bnd) == 0.0) spx->p_stat = LPX_P_FEAS; else spx->p_stat = LPX_P_INFEAS; if (spx_check_cbar(spx, spx->tol_dj) == 0.0) spx->d_stat = LPX_D_FEAS; else spx->d_stat = LPX_D_INFEAS; /* display information about the final basic solution */ if (spx->msg_lev >= 2 && spx->it_cnt % spx->out_frq != 0 && spx->out_dly <= spent) dual_opt_dpy(spx); /* correct the preliminary diagnosis */ switch (ret) { case LPX_E_OK: /* assumed LPX_P_FEAS and LPX_D_FEAS */ if (spx->d_stat != LPX_D_FEAS) ret = LPX_E_INSTAB; else if (spx->p_stat != LPX_P_FEAS) { /* it seems we need to continue the search */ goto beg; } break; case LPX_E_OBJLL: case LPX_E_OBJUL: /* assumed LPX_P_INFEAS and LPX_D_FEAS */ if (spx->d_stat != LPX_D_FEAS) ret = LPX_E_INSTAB; else if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; else if (spx->dir == LPX_MIN && obj < spx->obj_ul || spx->dir == LPX_MAX && obj > spx->obj_ll) { /* it seems we need to continue the search */ goto beg; } break; case LPX_E_ITLIM: case LPX_E_TMLIM: /* assumed LPX_P_INFEAS and LPX_D_FEAS */ if (spx->d_stat != LPX_D_FEAS) ret = LPX_E_INSTAB; else if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; break; case LPX_E_NOFEAS: /* assumed LPX_P_INFEAS and LPX_D_FEAS */ if (spx->d_stat != LPX_D_FEAS) ret = LPX_E_INSTAB; else if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; else spx->p_stat = LPX_P_NOFEAS; break; case LPX_E_INSTAB: /* assumed LPX_D_INFEAS */ if (spx->d_stat == LPX_D_FEAS) { if (spx->p_stat == LPX_P_FEAS) ret = LPX_E_OK; else { /* it seems we need to continue the search */ goto beg; } } break; default: insist(ret != ret); } done: /* deallocate the working segment */ if (spx->meth != 0) { spx->meth = 0; ufree(spx->zeta); ufree(spx->ap); ufree(spx->aq); ufree(spx->dvec); if (spx->price) ufree(spx->refsp); ufree(spx->work); } /* determine the spent amount of time */ spent = utime() - start; /* decrease the time limit by the spent amount */ if (spx->tm_lim >= 0.0) { spx->tm_lim -= spent; if (spx->tm_lim < 0.0) spx->tm_lim = 0.0; } /* return to the calling program */ return ret; }
GC xGetColorGC(Display *display, Colormap cmap, x_color_list_index_t *list_index, const char *colorname) { int pixval; int get_next; x_color_list_t *new_entry, *this_entry; if (list_index->n_entries == 0) { new_entry = (x_color_list_t *) umalloc (sizeof(x_color_list_t)); list_index->first_entry = new_entry; } else { this_entry = list_index->first_entry; get_next = TRUE; while (get_next) { if (!strcmp(colorname, this_entry->colorname)) return(this_entry->gc); if (this_entry->next == NULL) { get_next = FALSE; } else { this_entry = this_entry->next; } /* if (this_entry->next == NULL) */ } /* while */ new_entry = (x_color_list_t *) ucalloc (1, sizeof(x_color_list_t)); this_entry->next = new_entry; } /* if (list_index ..... */ list_index->n_entries++; new_entry->next = NULL; new_entry->duplicate = FALSE; new_entry->colorname = (char *) umalloc (strlen(colorname) + 1); strcpy(new_entry->colorname, colorname); if (XParseColor(display, cmap, colorname, &new_entry->x_color) == 0) { fprintf(stderr, "ERROR - XParseColor\n"); fprintf(stderr, "Cannot match color '%s'\n", colorname); return(NULL); } XAllocColor(display, cmap, &new_entry->x_color); new_entry->gc = XCreateGC(display, DefaultRootWindow(display), 0, 0); XSetForeground(display, new_entry->gc, new_entry->x_color.pixel); /* * search through the list to check whether the same pixel value has * been allocated to a previous entry - this sometimes happens * if the server has run out of color cells. If there is a duplicate * entry, set the duplicate flag in the new entry */ pixval = new_entry->x_color.pixel; this_entry = list_index->first_entry; while (this_entry->next != NULL) { if (this_entry->x_color.pixel == pixval) { new_entry->duplicate = TRUE; break; } this_entry = this_entry->next; } /* while */ return(new_entry->gc); }
static void restore(struct dsa *dsa, double row_pval[], double row_dval[], double col_pval[], double col_dval[]) { /* restore solution of original LP */ LPX *lp = dsa->lp; int orig_m = dsa->orig_m; int orig_n = dsa->orig_n; int *ref = dsa->ref; int m = dsa->m; double *x = dsa->x; double *y = dsa->y; int dir = lpx_get_obj_dir(lp); int i, j, k, type, t, len, *ind; double lb, ub, rii, sjj, temp, *val; /* compute primal values of structural variables */ for (k = 1; k <= orig_n; k++) { j = ref[orig_m+k]; type = lpx_get_col_type(lp, k); sjj = lpx_get_sjj(lp, k); lb = lpx_get_col_lb(lp, k) / sjj; ub = lpx_get_col_ub(lp, k) / sjj; switch (type) { case LPX_FR: /* source: -inf < x < +inf */ /* result: x = x' - x'', x' >= 0, x'' >= 0 */ col_pval[k] = x[j] - x[j+1]; break; case LPX_LO: /* source: lb <= x < +inf */ /* result: x = lb + x', x' >= 0 */ col_pval[k] = lb + x[j]; break; case LPX_UP: /* source: -inf < x <= ub */ /* result: x = ub - x', x' >= 0 */ col_pval[k] = ub - x[j]; break; case LPX_DB: /* source: lb <= x <= ub */ /* result: x = lb + x', x' + x'' = ub - lb */ col_pval[k] = lb + x[j]; break; case LPX_FX: /* source: x = lb */ /* result: just substitute */ col_pval[k] = lb; break; default: insist(type != type); } } /* compute primal values of auxiliary variables */ /* xR = A * xS */ ind = ucalloc(1+orig_n, sizeof(int)); val = ucalloc(1+orig_n, sizeof(double)); for (k = 1; k <= orig_m; k++) { rii = lpx_get_rii(lp, k); temp = 0.0; len = lpx_get_mat_row(lp, k, ind, val); for (t = 1; t <= len; t++) { sjj = lpx_get_sjj(lp, ind[t]); temp += (rii * val[t] * sjj) * col_pval[ind[t]]; } row_pval[k] = temp; } ufree(ind); ufree(val); /* compute dual values of auxiliary variables */ for (k = 1; k <= orig_m; k++) { type = lpx_get_row_type(lp, k); i = ref[k]; switch (type) { case LPX_FR: insist(i == 0); row_dval[k] = 0.0; break; case LPX_LO: case LPX_UP: case LPX_DB: case LPX_FX: insist(1 <= i && i <= m); row_dval[k] = (dir == LPX_MIN ? +1.0 : -1.0) * y[i]; break; default: insist(type != type); } } /* compute dual values of structural variables */ /* dS = cS - A' * (dR - cR) */ ind = ucalloc(1+orig_m, sizeof(int)); val = ucalloc(1+orig_m, sizeof(double)); for (k = 1; k <= orig_n; k++) { sjj = lpx_get_sjj(lp, k); temp = lpx_get_obj_coef(lp, k) / sjj; len = lpx_get_mat_col(lp, k, ind, val); for (t = 1; t <= len; t++) { rii = lpx_get_rii(lp, ind[t]); temp -= (rii * val[t] * sjj) * row_dval[ind[t]]; } col_dval[k] = temp; } ufree(ind); ufree(val); /* unscale solution of original LP */ for (i = 1; i <= orig_m; i++) { rii = lpx_get_rii(lp, i); row_pval[i] /= rii; row_dval[i] *= rii; } for (j = 1; j <= orig_n; j++) { sjj = lpx_get_sjj(lp, j); col_pval[j] *= sjj; col_dval[j] /= sjj; } return; }
int setHWthreads(Step_t *step) { uint32_t node, lTID, tid, slotsSize, cpuCount, i, shift; uint32_t coreMapIndex = 0, coreArrayIndex = 0, coreArrayCount = 0; uint8_t *coreMap = NULL; int32_t lastCpu; int hwThreads, thread = 0, numThreads; JobCred_t *cred = step->cred; PSCPU_set_t CPUset; pininfo_t pininfo; /* generate slotlist */ slotsSize = step->np; PSpart_slot_t *slots = umalloc(slotsSize * sizeof(PSpart_slot_t)); /* get cpus from job credential */ if (!(coreMap = getCPUsForPartition(slots, step))) { mlog("%s: getting cpus for partition failed\n", __func__); goto error; } /* find start index for this step in core map that is job global */ Job_t *job = findJobById(step->jobid); if (job) { for (node=0; job && node < job->nrOfNodes; node++) { if (job->nodes[node] == step->nodes[0]) { /* we found the first node of our step */ mdbg(PSSLURM_LOG_PART, "%s: step start found: job node %u" " nodeid %u coreMapIndex %u coreArrayCount %u" " coreArrayIndex %u\n", __func__, node, job->nodes[node], coreMapIndex, coreArrayCount, coreArrayIndex); break; } /* get cpu count per node from job credential */ if (coreArrayIndex >= cred->coreArraySize) { mlog("%s: invalid job core array index %i, size %i\n", __func__, coreArrayIndex, cred->coreArraySize); goto error; } cpuCount = cred->coresPerSocket[coreArrayIndex] * cred->socketsPerNode[coreArrayIndex]; /* update global core map index to first core of the next node */ coreMapIndex += cpuCount; coreArrayCount++; if (coreArrayCount >= cred->sockCoreRepCount[coreArrayIndex]) { coreArrayIndex++; coreArrayCount = 0; } } } for (node=0; node < step->nrOfNodes; node++) { thread = 0; /* get cpu count per node from job credential */ if (coreArrayIndex >= cred->coreArraySize) { mlog("%s: invalid step core array index %i, size %i\n", __func__, coreArrayIndex, cred->coreArraySize); goto error; } cpuCount = cred->coresPerSocket[coreArrayIndex] * cred->socketsPerNode[coreArrayIndex]; hwThreads = PSIDnodes_getVirtCPUs(step->nodes[node]) / cpuCount; if (hwThreads < 1) hwThreads = 1; lastCpu = -1; /* no cpu assigned yet */ /* initialize pininfo struct (currently only used for RANK_LDOM) */ pininfo.usedHwThreads = ucalloc(cpuCount * hwThreads * sizeof(*pininfo.usedHwThreads)); pininfo.lastSocket = -1; /* set node and cpuset for every task on this node */ for (lTID=0; lTID < step->globalTaskIdsLen[node]; lTID++) { tid = step->globalTaskIds[node][lTID]; mdbg(PSSLURM_LOG_PART, "%s: node %u nodeid %u task %u tid" " %u coreMapIndex %u coreArrayCount %u" " coreArrayIndex %u\n", __func__, node, step->nodes[node], lTID, tid, coreMapIndex, coreArrayCount, coreArrayIndex); /* sanity check */ if (tid > slotsSize) { mlog("%s: invalid taskids '%s' slotsSize %u\n", __func__, PSC_printTID(tid), slotsSize); goto error; } /* calc CPUset */ setCPUset(&CPUset, step->cpuBindType, step->cpuBind, coreMap, coreMapIndex, cred->socketsPerNode[coreArrayIndex], cred->coresPerSocket[coreArrayIndex], cpuCount, &lastCpu, node, &thread, hwThreads, step->globalTaskIdsLen[node], step->tpp, lTID, &pininfo); slots[tid].node = step->nodes[node]; /* handle cyclic distribution */ if ((!(step->cpuBindType & (0xFFF & ~CPU_BIND_VERBOSE)) /* default */ || step->cpuBindType & (CPU_BIND_RANK | CPU_BIND_TO_THREADS)) && (step->taskDist == SLURM_DIST_BLOCK_CYCLIC || step->taskDist == SLURM_DIST_CYCLIC_CYCLIC)) { PSCPU_clrAll(slots[tid].CPUset); shift = (lTID % 2) ? cred->coresPerSocket[coreArrayIndex] : 0; shift = shift - step->tpp * ((lTID + 1) / 2); for (i = 0; i < (cpuCount * hwThreads); i++) { if (PSCPU_isSet(CPUset, i)) { PSCPU_setCPU(slots[tid].CPUset, (i + shift) % (cpuCount * hwThreads)); } } mdbg(PSSLURM_LOG_PART, "%s: Cyclic shifting by %d:\n", __func__, shift); mdbg(PSSLURM_LOG_PART, "- %s\n", PSCPU_print(CPUset)); mdbg(PSSLURM_LOG_PART, "+ %s\n", PSCPU_print(slots[tid].CPUset)); } else { PSCPU_copy(slots[tid].CPUset, CPUset); } } ufree(pininfo.usedHwThreads); /* update global core map index to first core of the next node */ coreMapIndex += cpuCount; coreArrayCount++; if (coreArrayCount >= cred->sockCoreRepCount[coreArrayIndex]) { coreArrayIndex++; coreArrayCount = 0; } } if ((numThreads = genThreads(slots, slotsSize, &step->hwThreads)) < 0) { goto error; } if (numThreads == 0) { mlog("%s: Error: numThreads == 0\n", __func__); goto error; } step->numHwThreads = numThreads; ufree(coreMap); ufree(slots); return 1; error: ufree(coreMap); ufree(slots); return 0; }