home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Frozen Fish 2: PC
/
frozenfish_august_1995.bin
/
bbs
/
d01xx
/
d0199.lha
/
ASimplex
/
main.c
< prev
next >
Wrap
C/C++ Source or Header
|
1989-03-31
|
9KB
|
293 lines
/*****************************************************************************
* Modul : main.c *
* Zweck : Simplexalgorithmus *
* Autor : Stefan F÷rster *
* *
* Datum | Version | Bemerkung *
* -----------|---------|--------------------------------------------------- *
* 14.03.1989 | 1.0 | *
* 15.03.1989 | | Zeitmessung mittels CurrentTime() *
* 17.03.1989 | 1.1 | SetTaskPri() jetzt korrekt *
* | | min cTx zugelassen *
* 18.03.1989 | 1.2 | Optional Ausgabe an ein File m÷glich (-f) *
*****************************************************************************/
IMPORT USHORT PhaseI(), PhaseII();
IMPORT BOOL MPSX(), SearchExpr();
IMPORT INT GetInput();
IMPORT SHORT GetExpr();
IMPORT VOID GiveMemBack(), GetRidOfLists(), PrintError(), Cap();
IMPORT VOID CurrentTime(), *OpenLibrary(), SetTaskPri(), fclose();
IMPORT struct Task *FindTask();
struct IntuitionBase *IntuitionBase = NULL;
DOUBLE INFINITE = 1.0/0.0; /* IEEE: NAN (Not A Number) */
FILE *file[2] = { NULL };
TEXT symbols[NUM_SYMBOLS][MAX_STRLEN+1];
BOOL minimize = _FALSE; /* _TRUE, falls Zielfunktion minimiert wird */
ITEMPTR list[NUM_LISTS];
TEXT args[BUFFER], line[BUFFER];
SHORT m, n, *B = NULL, *Nq = NULL, *Nminus = NULL;
DOUBLE c0, c0start;
DOUBLE *A = NULL, *AB1 = NULL, *b = NULL, *b2q = NULL;
DOUBLE *c = NULL, *c2 = NULL, *upper = NULL, *lower = NULL;
DOUBLE *x = NULL, *cq = NULL, *pi = NULL, *dq = NULL, *help = NULL;
STRPTR errors[] = {
(STRPTR)"Invalid arguments for \"load\"",
(STRPTR)"Identifier too long",
(STRPTR)"Identifier declared twice",
(STRPTR)"Unknown Identifier",
(STRPTR)"Sections have to start in column 1",
(STRPTR)"Section defined twice",
(STRPTR)"Unknown section",
(STRPTR)"Illegal order of sections",
(STRPTR)"Missing NAME-section (1st section) or NAME-section empty",
(STRPTR)"Missing ROWS-section (2nd section) or ROWS-section empty",
(STRPTR)"Missing goal or goal not found",
(STRPTR)"Missing COLUMNS-section (3rd section) or COLUMNS-section empty",
(STRPTR)"Missing RHS-section (4th section)",
(STRPTR)"Missing ENDATA-section (last section)",
(STRPTR)"Constraint must be of type N, E, L or G",
(STRPTR)"Bound must be of type UP or LO",
(STRPTR)"Lower bound > upper bound",
(STRPTR)"Expression in RANGES belongs to a \"E\"-constraint",
(STRPTR)"Can\'t find necessary expression in this line",
(STRPTR)"File-name too long",
(STRPTR)"Can\'t open file for read access",
(STRPTR)"Can\'t open file for write access",
(STRPTR)"End-of-file reached",
(STRPTR)"Not enough memory",
(STRPTR)"FATAL ERROR (This error should not occur, reboot system!)"
};
main()
{
INT error;
SHORT start, stop, length, i;
BOOL end = _FALSE;
USHORT verbose = 0, result;
TEXT ch;
STRPTR sptr;
ULONG iter1, iter2, sec1, sec2, micro1, micro2;
LONG h, min, sec, sec100, pri = 0L;
SHORT atoi();
VOID PrintSolution(), Leave();
/* Zuerst Intuition-Bibliothek ÷ffnen */
if(!(IntuitionBase = OpenLibrary("intuition.library",LIBRARY_VERSION))) {
Leave("Can't find \"intuition.library\"!");
return;
}
puts("\f\033[1mASimplex Version 1.2");
puts("THE Amiga Simplex Program");
puts("(c) 18.03.1989 Stefan F÷rster\033[0m\n\n");
FOREVER {
printf(">> ");
if(error = GetInput(args)) {
PrintError(error,NULL);
Leave("");
}
Cap(args,0,BUFFER);
if(SearchExpr(args,&start,&stop)) {
length = GetExpr(line,args,start,stop);
if(strcmp(line,"HELP") == 0) {
puts(" HELP");
puts(" LOAD <file> [-cGOAL] [-bRHS] [-rRANGE] [-uBOUND] [-m] \
[-fFILE]");
puts(" VERBOSE");
puts(" PRIORITY [N]");
puts(" QUIT");
}
else if(strcmp(line,"QUIT") == 0) {
do {
printf("?? Really [Y,N] ? ");
if(error = GetInput(args)) {
PrintError(error,NULL);
Leave("");
}
Cap(args,0,BUFFER);
if(!SearchExpr(args,&start,&stop)) start = 0;
} while((ch = *(args+start))!='N' && ch!='Y');
if(ch == 'Y') Leave("");
}
else if(strcmp(line,"VERBOSE") == 0) {
verbose = verbose ? 0 : VERBOSE;
if(verbose) puts(" VERBOSE ON");
else puts(" VERBOSE OFF");
}
else if(strcmp(line,"PRIORITY") == 0) {
sptr = args+stop+1;
if(SearchExpr(sptr,&start,&stop)) {
length = GetExpr(line,sptr,start,stop);
pri = (LONG)atoi(line);
if(pri<0L) pri = 0L;
if(pri>20L) pri = 20L;
SetTaskPri(FindTask((STRPTR)0),pri);
printf(" Changed task priority to %ld.\n",pri);
}
else printf(" Current task priority is %ld.\n",pri);
}
else if(strcmp(line,"LOAD") == 0) {
CurrentTime(&sec1,µ1);
if(MPSX(args+stop+1)) {
if(!verbose) puts("@@ Please wait - calculation.");
iter1 = iter2 = 0L;
result = PhaseI(&m,&n,B,Nq,A,AB1,b,b2q,c,c2,&c0,c0start,verbose,
upper,x,cq,pi,dq,Nminus,help,&iter1);
if(result == NOT_INVERTABLE) {
puts(" Matrix AB is not invertable.");
if(file[1]) fputs(" Matrix AB is not invertable.\n",file[1]);
}
else if(result == UNBOUNDED) {
puts(" PHASE I IS UNBOUNDED. THIS SHOULD NOT OCCUR!!");
if(file[1])
fputs(" PHASE I IS UNBOUNDED. THIS SHOULD NOT OCCUR!!\n",file[1]);
}
else if(result == EMPTY) {
puts(" This problem is not solveable.");
if(file[1]) fputs(" This problem is not solveable.\n",file[1]);
}
else if(result == CLEAR_CUT) PrintSolution();
else {
result = PhaseII(m,n,B,Nq,A,AB1,b,b2q,c,&c0,c0start,
verbose|PHASE_II,upper,lower,x,cq,pi,dq,Nminus,help,&iter2);
if(result == NOT_INVERTABLE) {
puts(" Matrix AB is not invertable.");
if(file[1]) fputs(" Matrix AB is not invertable.\n",file[1]);
}
else if(result == UNBOUNDED) {
puts(" This problem is unbounded.");
if(file[1]) fputs(" This problem is unbounded.\n",file[1]);
}
else PrintSolution();
}
printf("-> %ld iterations needed.\n",iter1+iter2);
if(file[1]) fprintf(file[1],"-> %ld iterations needed.\n",iter1+iter2);
GiveMemBack();
GetRidOfLists();
minimize = _FALSE;
}
CurrentTime(&sec2,µ2);
sec100 = micro2-micro1;
sec = sec2-sec1;
if(sec100 < 0L) {
sec100 += 1000000L;
--sec;
}
sec100 /= 10000L;
h = sec/3600L;
min = (sec-3600L*h)/60;
sec -= 3600L*h+60*min;
printf("-> Used time: %3ld : %02ld : %02ld,%02ld\n",h,min,sec,sec100);
if(file[1]) {
fprintf(file[1],"-> Used time: %3ld : %02ld : %02ld,%02ld\f",h,min,
sec,sec100);
fclose(file[1]);
file[1] = NULL;
}
if(file[0]) {
fclose(file[0]);
file[0] = NULL;
}
}
else printf(" Unknown command \"%s\".\n",line);
}
} /* FOREVER */
}
/*****************************************************************************
* VOID PrintSolution() *
* Ausgabe der L÷sung *
*****************************************************************************/
VOID PrintSolution()
{
VOID PrintX();
puts("@@ Solution:\n");
printf(" %-9s = %14.10lg\n",symbols[GOAL],minimize ? -c0 : c0);
PrintX(list[VAR_LIST],stdout);
puts("");
if(file[1]) {
fputs("@@ Solution:\n\n",file[1]);
fprintf(file[1]," %-9s = %14.10lg\n",symbols[GOAL],minimize ? -c0 : c0);
PrintX(list[VAR_LIST],file[1]);
fputs("\n",file[1]);
}
}
/*****************************************************************************
* VOID PrintX() *
* Gibt das Ergebnis der Berechnungen aus. *
*****************************************************************************/
VOID PrintX(ptr,fptr)
ITEMPTR ptr;
FILE *fptr;
{
if(ptr) {
PrintX(ptr->next,fptr);
fprintf(fptr," %-9s = %14.10lg\n",ptr->string,x[ptr->nr-1]);
}
}
/*****************************************************************************
* VOID Leave() *
* Verlassen des Programms *
*****************************************************************************/
VOID Leave(str)
STRPTR str;
{
if(IntuitionBase) CloseLibrary(IntuitionBase);
fprintf(stderr,"\n%s\n\n",str);
exit(0);
}