📄 glpmpl04.c
字号:
/*------------------------------------------------------------------------ write_char - write next character to output text file.---- This routine writes a next ASCII character to the output text file.-- Note that line buffering is used, i.e. characters are stored in the-- output buffer until the new-line control character is passed, which-- causes actual writing data from the buffer to the output file. */void write_char(MPL *mpl, int c){ xassert(mpl->out_fp != NULL); xassert(mpl->out_cnt < OUTBUF_SIZE); if (c == '\n') { /* flush the output buffer */ mpl->out_buf[mpl->out_cnt] = '\0'; if (mpl->out_fp == stdout) xprintf("%s\n", mpl->out_buf); else fprintf(mpl->out_fp, "%s\n", mpl->out_buf); mpl->out_cnt = 0; } else { /* store the character to the output buffer */ mpl->out_buf[mpl->out_cnt++] = (char)c; if (mpl->out_cnt == OUTBUF_SIZE) error(mpl, "write error on %s - output buffer overflow", mpl->out_file); } return;}/*------------------------------------------------------------------------ write_text - format and write text to output text file.---- This routine formats a text using the format control string and then-- writes this text to the output text file. */void write_text(MPL *mpl, char *fmt, ...){ va_list arg; char buf[OUTBUF_SIZE], *c; va_start(arg, fmt); vsprintf(buf, fmt, arg); xassert(strlen(buf) < sizeof(buf)); va_end(arg); for (c = buf; *c != '\0'; c++) write_char(mpl, *c); return;}/*------------------------------------------------------------------------ flush_output - finalize writing data to output text file.---- This routine finalizes writing data to the output text file. */void flush_output(MPL *mpl){ xassert(mpl->out_fp != NULL); if (mpl->out_cnt > 0) write_char(mpl, '\n'); if (mpl->out_fp != stdout) { fflush(mpl->out_fp); if (ferror(mpl->out_fp)) error(mpl, "write error on %s - %s", mpl->out_file, strerror(errno)); } return;}/**********************************************************************//* * * SOLVER INTERFACE * * *//**********************************************************************//*------------------------------------------------------------------------ error - print error message and terminate model processing.---- This routine formats and prints an error message and then terminates-- model processing. */void error(MPL *mpl, char *fmt, ...){ va_list arg; char msg[4095+1]; va_start(arg, fmt); vsprintf(msg, fmt, arg); xassert(strlen(msg) < sizeof(msg)); va_end(arg); switch (mpl->phase) { case 1: case 2: /* translation phase */ xprintf("%s:%d: %s\n", mpl->in_file == NULL ? "(unknown)" : mpl->in_file, mpl->line, msg); print_context(mpl); break; case 3: /* generation/postsolve phase */ xprintf("%s:%d: %s\n", mpl->mod_file == NULL ? "(unknown)" : mpl->mod_file, mpl->stmt == NULL ? 0 : mpl->stmt->line, msg); break; default: xassert(mpl != mpl); } mpl->phase = 4; longjmp(mpl->jump, 1); /* no return */}/*------------------------------------------------------------------------ warning - print warning message and continue model processing.---- This routine formats and prints a warning message and returns to the-- calling program. */void warning(MPL *mpl, char *fmt, ...){ va_list arg; char msg[4095+1]; va_start(arg, fmt); vsprintf(msg, fmt, arg); xassert(strlen(msg) < sizeof(msg)); va_end(arg); switch (mpl->phase) { case 1: case 2: /* translation phase */ xprintf("%s:%d: warning: %s\n", mpl->in_file == NULL ? "(unknown)" : mpl->in_file, mpl->line, msg); break; case 3: /* generation/postsolve phase */ xprintf("%s:%d: warning: %s\n", mpl->mod_file == NULL ? "(unknown)" : mpl->mod_file, mpl->stmt == NULL ? 0 : mpl->stmt->line, msg); break; default: xassert(mpl != mpl); } return;}/*------------------------------------------------------------------------ mpl_initialize - create and initialize translator database.---- *Synopsis*---- #include "glpmpl.h"-- MPL *mpl_initialize(void);---- *Description*---- The routine mpl_initialize creates and initializes the database used-- by the GNU MathProg translator.---- *Returns*---- The routine returns a pointer to the database created. */MPL *mpl_initialize(void){ MPL *mpl; mpl = xmalloc(sizeof(MPL)); /* scanning segment */ mpl->line = 0; mpl->c = 0; mpl->token = 0; mpl->imlen = 0; mpl->image = xcalloc(MAX_LENGTH+1, sizeof(char)); mpl->image[0] = '\0'; mpl->value = 0.0; mpl->b_token = 0; mpl->b_imlen = 0; mpl->b_image = xcalloc(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 = xcalloc(MAX_LENGTH+1, sizeof(char)); mpl->f_image[0] = '\0'; mpl->f_value = 0.0; mpl->context = xcalloc(CONTEXT_SIZE, sizeof(char)); memset(mpl->context, ' ', CONTEXT_SIZE); mpl->c_ptr = 0; mpl->flag_d = 0; /* translating segment */ mpl->pool = dmp_create_poolx(0); mpl->tree = avl_create_tree(avl_strcmp, NULL); 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_poolx(sizeof(STRING)); mpl->symbols = dmp_create_poolx(sizeof(SYMBOL)); mpl->tuples = dmp_create_poolx(sizeof(TUPLE)); mpl->arrays = dmp_create_poolx(sizeof(ARRAY)); mpl->members = dmp_create_poolx(sizeof(MEMBER)); mpl->elemvars = dmp_create_poolx(sizeof(ELEMVAR)); mpl->formulae = dmp_create_poolx(sizeof(FORMULA)); mpl->elemcons = dmp_create_poolx(sizeof(ELEMCON)); mpl->a_list = NULL; mpl->sym_buf = xcalloc(255+1, sizeof(char)); mpl->sym_buf[0] = '\0'; mpl->tup_buf = xcalloc(255+1, sizeof(char)); mpl->tup_buf[0] = '\0'; /* generating/postsolving segment */ mpl->rand = rng_create_rand(); mpl->flag_p = 0; mpl->stmt = NULL;#if 1 /* 11/II-2008 */ mpl->dca = NULL;#endif 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;#if 1 /* 14/VII-2006 */ mpl->prt_fp = NULL; mpl->prt_file = NULL;#endif /* solver interface segment */ if (setjmp(mpl->jump)) xassert(mpl != mpl); mpl->phase = 0; mpl->mod_file = NULL; mpl->mpl_buf = xcalloc(255+1, sizeof(char)); mpl->mpl_buf[0] = '\0'; return mpl;}/*------------------------------------------------------------------------ mpl_read_model - read model section and optional data section.---- *Synopsis*---- #include "glpmpl.h"-- int mpl_read_model(MPL *mpl, char *file, int skip_data);---- *Description*---- The routine mpl_read_model reads model section and optionally data-- section, which may follow the model section, from the text file,-- whose name is the character string file, performs translating model-- statements and data blocks, and stores all the information in the-- translator database.---- The parameter skip_data is a flag. If the input file contains the-- data section and this flag is set, the data section is not read as-- if there were no data section and a warning message is issued. This-- allows reading the data section from another input file.---- This routine should be called once after the routine mpl_initialize-- and before other API routines.---- *Returns*---- The routine mpl_read_model returns one the following codes:---- 1 - translation successful. The input text file contains only model-- section. In this case the calling program may call the routine-- mpl_read_data to read data section from another file.-- 2 - translation successful. The input text file contains both model-- and data section.-- 4 - processing failed due to some errors. In this case the calling-- program should call the routine mpl_terminate to terminate model-- processing. */int mpl_read_model(MPL *mpl, char *file, int skip_data){ if (mpl->phase != 0) xfault("mpl_read_model: invalid call sequence\n"); if (file == NULL) xfault("mpl_read_model: no input filename specified\n"); /* set up error handler */ if (setjmp(mpl->jump)) goto done; /* translate model section */ mpl->phase = 1; xprintf("Reading model section from %s...\n", file); open_input(mpl, file); model_section(mpl); if (mpl->model == NULL) error(mpl, "empty model section not allowed"); /* save name of the input text file containing model section for error diagnostics during the generation phase */ mpl->mod_file = xcalloc(strlen(file)+1, sizeof(char)); strcpy(mpl->mod_file, mpl->in_file); /* allocate content arrays for all model objects */ alloc_content(mpl); /* optional data section may begin with the keyword 'data' */ if (is_keyword(mpl, "data")) { if (skip_data) { warning(mpl, "data section ignored"); goto skip; } mpl->flag_d = 1; get_token(mpl /* data */); if (mpl->token != T_SEMICOLON) error(mpl, "semicolon missing where expected"); get_token(mpl /* ; */); /* translate data section */ mpl->phase = 2; xprintf("Reading data section from %s...\n", file); data_section(mpl); } /* process end statement */ end_statement(mpl);skip: xprintf("%d line%s were read\n", mpl->line, mpl->line == 1 ? "" : "s"); close_input(mpl);done: /* return to the calling program */ return mpl->phase;}/*------------------------------------------------------------------------ mpl_read_data - read data section.---- *Synopsis*---- #include "glpmpl.h"-- int mpl_read_data(MPL *mpl, char *file);---- *Description*---- The routine mpl_read_data reads data section from the text file,-- whose name is the character string file, performs translating data-- blocks, and stores the data read in the translator database.---- If this routine is used, it should be called once after the routine-- mpl_read_model and if the latter returned the code 1.---- *Returns*---- The routine mpl_read_data returns one of the following codes:---- 2 - data section has been successfully processed.-- 4 - processing failed due to some errors. In this case the calling-- program should call the routine mpl_terminate to terminate model-- processing. */int mpl_read_data(MPL *mpl, char *file)#if 0 /* 02/X-2008 */{ if (mpl->phase != 1)#else{ if (!(mpl->phase == 1 || mpl->phase == 2))#endif xfault("mpl_read_data: invalid call sequence\n"); if (file == NULL) xfault("mpl_read_data: no input filename specified\n"); /* set up error handler */ if (setjmp(mpl->jump)) goto done; /* process data section */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -