sq_lpsolve.cpp 32 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149
  1. #if defined(SQ_USE_LPSOLVE) || defined(SQ_USE_LPSOLVE_STATIC)
  2. #include <ctype.h>
  3. #include <string.h>
  4. #include <stdio.h>
  5. #include "squirrel.h"
  6. #include "sqstdblobimpl.h"
  7. #include "lp_lib.h"
  8. ////////
  9. #include "dynamic_library.h"
  10. /*SquiLu
  11. local library_functions = [
  12. ["void", "lp_solve_version", "int *majorversion, int *minorversion, int *release, int *build"],
  13. ["lprec*", "make_lp", "int rows, int columns"],
  14. ["MYBOOL", "resize_lp", "lprec *lp, int rows, int columns"],
  15. ["lprec*", "read_LP", "char *filename, int verbose, char *lp_name"],
  16. ["lprec*", "read_MPS", "char *filename, int options"],
  17. ["lprec*", "read_freeMPS", "char *filename, int options"],
  18. ["void", "delete_lp", "lprec *plp"],
  19. //next entry should be the last one
  20. //to make valid the test made on load_library function
  21. ["void", "free_lp", "lprec **plp"],
  22. ];
  23. function write_library_functions_declaration(){
  24. foreach(k,v in library_functions) {
  25. putsnl("typedef " + v[0] + " (*" + v[1] + "_t)(" + v[2] + ");");
  26. putsnl("static " + v[1] + "_t dl" + v[1] + " = 0;");
  27. }
  28. }
  29. function write_library_functions_load(){
  30. foreach(k,v in library_functions){
  31. putsnl("dl" + v[1] + " = (" + v[1] + "_t) libdyn.dlsym(\"" + v[1] + "\");");
  32. putsnl("if(!dl" + v[1] + ") return false;");
  33. }
  34. }
  35. function write_library_functions_static_defines(){
  36. foreach(k,v in library_functions){
  37. putsnl("#define dl" + v[1] + " " + v[1]);
  38. }
  39. }
  40. SquiLu*/
  41. #ifdef SQ_USE_LPSOLVE_STATIC
  42. #define load_library(x) true
  43. //@write_library_functions_static_defines()
  44. // generated-code:begin
  45. #define dllp_solve_version lp_solve_version
  46. #define dlmake_lp make_lp
  47. #define dlresize_lp resize_lp
  48. #define dlread_LP read_LP
  49. #define dlread_MPS read_MPS
  50. #define dlread_freeMPS read_freeMPS
  51. #define dldelete_lp delete_lp
  52. #define dlfree_lp free_lp
  53. // generated-code:end
  54. #else
  55. static DynamicLibrary libdyn;
  56. //@write_library_functions_declaration();
  57. // generated-code:begin
  58. typedef void (*lp_solve_version_t)(int *majorversion, int *minorversion, int *release, int *build);
  59. static lp_solve_version_t dllp_solve_version = 0;
  60. typedef lprec* (*make_lp_t)(int rows, int columns);
  61. static make_lp_t dlmake_lp = 0;
  62. typedef MYBOOL (*resize_lp_t)(lprec *lp, int rows, int columns);
  63. static resize_lp_t dlresize_lp = 0;
  64. typedef lprec* (*read_LP_t)(char *filename, int verbose, char *lp_name);
  65. static read_LP_t dlread_LP = 0;
  66. typedef lprec* (*read_MPS_t)(char *filename, int options);
  67. static read_MPS_t dlread_MPS = 0;
  68. typedef lprec* (*read_freeMPS_t)(char *filename, int options);
  69. static read_freeMPS_t dlread_freeMPS = 0;
  70. typedef void (*delete_lp_t)(lprec *plp);
  71. static delete_lp_t dldelete_lp = 0;
  72. typedef void (*free_lp_t)(lprec **plp);
  73. static free_lp_t dlfree_lp = 0;
  74. // generated-code:end
  75. static const char *dynamicLibName = DYNLIB_FOR_OS(liblpsolve55);
  76. static bool load_library(const char *libname)
  77. {
  78. if(dlfree_lp) return true;
  79. if(libdyn.open(libname))
  80. {
  81. //@write_library_functions_load();
  82. // generated-code:begin
  83. dllp_solve_version = (lp_solve_version_t) libdyn.dlsym("lp_solve_version");
  84. if(!dllp_solve_version) return false;
  85. dlmake_lp = (make_lp_t) libdyn.dlsym("make_lp");
  86. if(!dlmake_lp) return false;
  87. dlresize_lp = (resize_lp_t) libdyn.dlsym("resize_lp");
  88. if(!dlresize_lp) return false;
  89. dlread_LP = (read_LP_t) libdyn.dlsym("read_LP");
  90. if(!dlread_LP) return false;
  91. dlread_MPS = (read_MPS_t) libdyn.dlsym("read_MPS");
  92. if(!dlread_MPS) return false;
  93. dlread_freeMPS = (read_freeMPS_t) libdyn.dlsym("read_freeMPS");
  94. if(!dlread_freeMPS) return false;
  95. dldelete_lp = (delete_lp_t) libdyn.dlsym("delete_lp");
  96. if(!dldelete_lp) return false;
  97. dlfree_lp = (free_lp_t) libdyn.dlsym("free_lp");
  98. if(!dlfree_lp) return false;
  99. // generated-code:end
  100. return true;
  101. }
  102. return false;
  103. }
  104. #endif // SQ_USE_LPSOLVE_STATIC
  105. SQ_OPT_STRING_STRLEN();
  106. static const SQChar LPSOLVE_Tag[] = _SC("SQLPSolve");
  107. #define GET_lpsolve_INSTANCE() SQ_GET_INSTANCE(v, 1, lprec, LPSOLVE_Tag) \
  108. if(self == NULL) return sq_throwerror(v, _SC("sqlpsolve object already closed"));
  109. static SQRESULT sq_lpsolve_releasehook(SQUserPointer p, SQInteger /*size*/, void */*ep*/)
  110. {
  111. lprec *self = ((lprec *)p);
  112. if(self)
  113. {
  114. dldelete_lp(self);
  115. }
  116. return 1;
  117. }
  118. static SQRESULT sq_lpsolve_constructor(HSQUIRRELVM v)
  119. {
  120. //if(!load_library(dynamicLibName)) return sq_throwerror(v, _SC("Failed to load liblpsolve !"));
  121. SQ_FUNC_VARS_NO_TOP(v);
  122. SQ_GET_INTEGER(v, 2, constraints);
  123. SQ_GET_INTEGER(v, 3, variables);
  124. lprec *self = dlmake_lp(constraints, variables);
  125. self->set_verbose(self, IMPORTANT);
  126. sq_setinstanceup(v,1,self);
  127. sq_setreleasehook(v,1,sq_lpsolve_releasehook);
  128. return 0;
  129. }
  130. static SQRESULT sq_lpsolve_version(HSQUIRRELVM v)
  131. {
  132. int majorversion, minorversion, release, build;
  133. dllp_solve_version(&majorversion, &minorversion, &release, &build);
  134. sq_pushfstring(v,_SC("lp_solve %d.%d.%d.%d"), majorversion, minorversion, release, build);
  135. return 1;
  136. }
  137. static SQRESULT sq_lpsolve_resize_lp(HSQUIRRELVM v)
  138. {
  139. SQ_FUNC_VARS_NO_TOP(v);
  140. GET_lpsolve_INSTANCE();
  141. SQ_GET_INTEGER(v, 2, rows);
  142. SQ_GET_INTEGER(v, 3, cols);
  143. sq_pushbool(v, self->resize_lp(self, rows, cols));
  144. return 1;
  145. }
  146. static SQRESULT sq_lpsolve_loadlib(HSQUIRRELVM v)
  147. {
  148. SQ_FUNC_VARS_NO_TOP(v);
  149. SQ_GET_STRING(v, 2, libname);
  150. sq_pushbool(v, load_library(libname));
  151. return 1;
  152. }
  153. static SQRESULT sq_lpsolve_set_verbose(HSQUIRRELVM v)
  154. {
  155. SQ_FUNC_VARS_NO_TOP(v);
  156. GET_lpsolve_INSTANCE();
  157. SQ_GET_INTEGER(v, 2, mode);
  158. //dlset_verbose(self, mode);
  159. self->set_verbose(self, mode);
  160. return 0;
  161. }
  162. static SQRESULT isSQFloat64Array(HSQUIRRELVM v, SQInteger idx)
  163. {
  164. SQInteger atype;
  165. if(sq_arraygettype(v, idx, &atype) != SQ_OK && atype == eat_SQFloat64Array) return sq_throwerror(v, _SC("SQFloat64Array expected"));
  166. return SQ_OK;
  167. }
  168. #define IS_SQFloat64Array(idx) if((_rc_ =isSQFloat64Array(v, idx))) return _rc_;
  169. static SQRESULT sq_lpsolve_set_obj_fn(HSQUIRRELVM v)
  170. {
  171. SQ_FUNC_VARS_NO_TOP(v);
  172. GET_lpsolve_INSTANCE();
  173. const SQInteger ary_idx = 2;
  174. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  175. {
  176. void *ary;
  177. IS_SQFloat64Array(ary_idx);
  178. sq_arraygetrawdata(v, ary_idx, &ary);
  179. sq_pushbool(v, self->set_obj_fn(self, (REAL*)ary));
  180. }
  181. else sq_pushbool(v, SQFalse);
  182. return 1;
  183. }
  184. static SQRESULT sq_lpsolve_add_constraint(HSQUIRRELVM v)
  185. {
  186. SQ_FUNC_VARS_NO_TOP(v);
  187. GET_lpsolve_INSTANCE();
  188. const SQInteger ary_idx = 2;
  189. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  190. {
  191. void *ary;
  192. IS_SQFloat64Array(ary_idx);
  193. sq_arraygetrawdata(v, ary_idx, &ary);
  194. SQ_GET_INTEGER(v, 3, constr_type);
  195. SQ_GET_FLOAT(v, 4, rh);
  196. //for(SQInteger i= 0, len =sq_getsize(v, ary_idx); i < len; ++i) printf("add_constraint %d %f\n", (int) i, ((REAL*)ary)[i]);
  197. sq_pushbool(v, self->add_constraint(self, (REAL*)ary, constr_type, rh));
  198. }
  199. else sq_pushbool(v, SQFalse);
  200. return 1;
  201. }
  202. static SQRESULT sq_lpsolve_add_constraintex(HSQUIRRELVM v)
  203. {
  204. SQ_FUNC_VARS_NO_TOP(v);
  205. GET_lpsolve_INSTANCE();
  206. SQ_GET_INTEGER(v, 2, asize);
  207. const SQInteger ary_row_idx = 3;
  208. const SQInteger ary_col_idx = 4;
  209. if(sq_gettype(v, ary_row_idx) == OT_ARRAY)
  210. {
  211. SQInteger atype;
  212. if(sq_arraygettype(v, ary_row_idx, &atype) != SQ_OK && atype == eat_SQFloat64Array) return sq_throwerror(v, _SC("SQFloat64Array for rows expected"));
  213. if(sq_arraygettype(v, ary_col_idx, &atype) != SQ_OK && atype == eat_SQInt32Array) return sq_throwerror(v, _SC("SQInt32Array for cols expected"));
  214. void *ary_row, *ary_col;
  215. sq_arraygetrawdata(v, ary_row_idx, &ary_row);
  216. sq_arraygetrawdata(v, ary_col_idx, &ary_col);
  217. SQ_GET_INTEGER(v, 5, constr_type);
  218. SQ_GET_FLOAT(v, 6, rh);
  219. //for(SQInteger i= 0, len =sq_getsize(v, ary_idx); i < len; ++i) printf("add_constraint %d %f\n", (int) i, ((REAL*)ary)[i]);
  220. sq_pushbool(v, self->add_constraintex(self, asize, (REAL*)ary_row, (int*)ary_col, constr_type, rh));
  221. }
  222. else sq_pushbool(v, SQFalse);
  223. return 1;
  224. }
  225. static SQRESULT sq_lpsolve_set_lowbo(HSQUIRRELVM v)
  226. {
  227. SQ_FUNC_VARS_NO_TOP(v);
  228. GET_lpsolve_INSTANCE();
  229. SQ_GET_INTEGER(v, 2, colnr);
  230. SQ_GET_FLOAT(v, 3, val);
  231. sq_pushbool(v, self->set_lowbo(self, colnr, val));
  232. return 1;
  233. }
  234. static SQRESULT sq_lpsolve_set_upbo(HSQUIRRELVM v)
  235. {
  236. SQ_FUNC_VARS_NO_TOP(v);
  237. GET_lpsolve_INSTANCE();
  238. SQ_GET_INTEGER(v, 2, rownr);
  239. SQ_GET_FLOAT(v, 3, val);
  240. sq_pushbool(v, self->set_upbo(self, rownr, val));
  241. return 1;
  242. }
  243. static SQRESULT sq_lpsolve_set_bounds(HSQUIRRELVM v)
  244. {
  245. SQ_FUNC_VARS_NO_TOP(v);
  246. GET_lpsolve_INSTANCE();
  247. SQ_GET_INTEGER(v, 2, colno)
  248. SQ_GET_FLOAT(v, 3, lb);
  249. SQ_GET_FLOAT(v, 4, ub);
  250. sq_pushbool(v, self->set_bounds(self, colno, lb, ub));
  251. return 1;
  252. }
  253. static SQRESULT sq_lpsolve_set_col_name(HSQUIRRELVM v)
  254. {
  255. SQ_FUNC_VARS_NO_TOP(v);
  256. GET_lpsolve_INSTANCE();
  257. SQ_GET_INTEGER(v, 2, colnr);
  258. SQ_GET_STRING(v, 3, name);
  259. sq_pushbool(v, self->set_col_name(self, colnr, (SQChar*)name));
  260. return 1;
  261. }
  262. static SQRESULT sq_lpsolve_get_col_name(HSQUIRRELVM v)
  263. {
  264. SQ_FUNC_VARS_NO_TOP(v);
  265. GET_lpsolve_INSTANCE();
  266. SQ_GET_INTEGER(v, 2, colnr);
  267. sq_pushstring(v, self->get_col_name(self, colnr), -1);
  268. return 1;
  269. }
  270. static SQRESULT sq_lpsolve_set_row_name(HSQUIRRELVM v)
  271. {
  272. SQ_FUNC_VARS_NO_TOP(v);
  273. GET_lpsolve_INSTANCE();
  274. SQ_GET_INTEGER(v, 2, rownr);
  275. SQ_GET_STRING(v, 3, name);
  276. sq_pushbool(v, self->set_row_name(self, rownr, (SQChar*)name));
  277. return 1;
  278. }
  279. static SQRESULT sq_lpsolve_get_row_name(HSQUIRRELVM v)
  280. {
  281. SQ_FUNC_VARS_NO_TOP(v);
  282. GET_lpsolve_INSTANCE();
  283. SQ_GET_INTEGER(v, 2, rownr);
  284. sq_pushstring(v, self->get_row_name(self, rownr), -1);
  285. return 1;
  286. }
  287. static SQRESULT sq_lpsolve_set_lp_name(HSQUIRRELVM v)
  288. {
  289. SQ_FUNC_VARS_NO_TOP(v);
  290. GET_lpsolve_INSTANCE();
  291. SQ_GET_STRING(v, 2, name);
  292. sq_pushbool(v, self->set_lp_name(self, (SQChar*)name));
  293. return 1;
  294. }
  295. static SQRESULT sq_lpsolve_get_lp_name(HSQUIRRELVM v)
  296. {
  297. SQ_FUNC_VARS_NO_TOP(v);
  298. GET_lpsolve_INSTANCE();
  299. sq_pushstring(v, self->get_lp_name(self), -1);
  300. return 1;
  301. }
  302. static SQRESULT sq_lpsolve_write_lp(HSQUIRRELVM v)
  303. {
  304. SQ_FUNC_VARS_NO_TOP(v);
  305. GET_lpsolve_INSTANCE();
  306. SQ_GET_STRING(v, 2, filename);
  307. sq_pushbool(v, self->write_lp(self, (SQChar*)filename));
  308. return 1;
  309. }
  310. static SQRESULT sq_lpsolve_write_mps(HSQUIRRELVM v)
  311. {
  312. SQ_FUNC_VARS_NO_TOP(v);
  313. GET_lpsolve_INSTANCE();
  314. SQ_GET_STRING(v, 2, filename);
  315. sq_pushbool(v, self->write_mps(self, (SQChar*)filename));
  316. return 1;
  317. }
  318. static SQRESULT sq_lpsolve_write_basis(HSQUIRRELVM v)
  319. {
  320. SQ_FUNC_VARS_NO_TOP(v);
  321. GET_lpsolve_INSTANCE();
  322. SQ_GET_STRING(v, 2, filename);
  323. sq_pushbool(v, self->write_basis(self, (SQChar*)filename));
  324. return 1;
  325. }
  326. static SQRESULT sq_lpsolve_write_freemps(HSQUIRRELVM v)
  327. {
  328. SQ_FUNC_VARS_NO_TOP(v);
  329. GET_lpsolve_INSTANCE();
  330. SQ_GET_STRING(v, 2, filename);
  331. sq_pushbool(v, self->write_freemps(self, (SQChar*)filename));
  332. return 1;
  333. }
  334. static SQRESULT sq_lpsolve_write_params(HSQUIRRELVM v)
  335. {
  336. SQ_FUNC_VARS_NO_TOP(v);
  337. GET_lpsolve_INSTANCE();
  338. SQ_GET_STRING(v, 2, filename);
  339. SQ_GET_STRING(v, 3, options);
  340. sq_pushbool(v, self->write_params(self, (SQChar*)filename, (SQChar*)options));
  341. return 1;
  342. }
  343. static SQRESULT sq_lpsolve_read_problem(HSQUIRRELVM v, lprec *self)
  344. {
  345. if(self)
  346. {
  347. sq_pushstring(v, LPSOLVE_Tag, -1);
  348. if(sq_getonroottable(v) == SQ_OK){
  349. if(sq_createinstance(v, -1) == SQ_OK){
  350. sq_setinstanceup(v, -1, self);
  351. sq_setreleasehook(v,-1,sq_lpsolve_releasehook);
  352. }
  353. }
  354. }
  355. else sq_pushnull(v);
  356. return 1;
  357. }
  358. static SQRESULT sq_lpsolve_read_LP(HSQUIRRELVM v)
  359. {
  360. SQ_FUNC_VARS_NO_TOP(v);
  361. SQ_GET_STRING(v, 2, filename);
  362. SQ_GET_BOOL(v, 3, verbose);
  363. SQ_GET_STRING(v, 4, lp_name);
  364. lprec *self = dlread_LP((SQChar*)filename, verbose, (SQChar*)lp_name);
  365. return sq_lpsolve_read_problem(v, self);
  366. }
  367. static SQRESULT sq_lpsolve_read_MPS(HSQUIRRELVM v)
  368. {
  369. SQ_FUNC_VARS_NO_TOP(v);
  370. SQ_GET_STRING(v, 2, filename);
  371. SQ_GET_INTEGER(v, 3, options);
  372. lprec *self = dlread_MPS((SQChar*)filename, options);
  373. return sq_lpsolve_read_problem(v, self);
  374. }
  375. static SQRESULT sq_lpsolve_read_basis(HSQUIRRELVM v)
  376. {
  377. SQ_FUNC_VARS_NO_TOP(v);
  378. GET_lpsolve_INSTANCE();
  379. SQ_GET_STRING(v, 2, filename);
  380. sq_pushbool(v, self->read_params(self, (SQChar*)filename, NULL));
  381. return 1;
  382. }
  383. static SQRESULT sq_lpsolve_read_freeMPS(HSQUIRRELVM v)
  384. {
  385. SQ_FUNC_VARS_NO_TOP(v);
  386. SQ_GET_STRING(v, 2, filename);
  387. SQ_GET_INTEGER(v, 3, options);
  388. lprec *self = dlread_freeMPS((SQChar*)filename, options);
  389. return sq_lpsolve_read_problem(v, self);
  390. }
  391. static SQRESULT sq_lpsolve_read_params(HSQUIRRELVM v)
  392. {
  393. SQ_FUNC_VARS_NO_TOP(v);
  394. GET_lpsolve_INSTANCE();
  395. SQ_GET_STRING(v, 2, filename);
  396. SQ_GET_STRING(v, 3, options);
  397. sq_pushbool(v, self->read_params(self, (SQChar*)filename, (SQChar*)options));
  398. return 1;
  399. }
  400. static SQRESULT sq_lpsolve_get_mat(HSQUIRRELVM v)
  401. {
  402. SQ_FUNC_VARS_NO_TOP(v);
  403. GET_lpsolve_INSTANCE();
  404. SQ_GET_INTEGER(v, 2, rownr);
  405. SQ_GET_INTEGER(v, 3, colnr);
  406. sq_pushfloat(v, self->get_mat(self, rownr, colnr));
  407. return 1;
  408. }
  409. static SQRESULT sq_lpsolve_set_mat(HSQUIRRELVM v)
  410. {
  411. SQ_FUNC_VARS_NO_TOP(v);
  412. GET_lpsolve_INSTANCE();
  413. SQ_GET_INTEGER(v, 2, rownr);
  414. SQ_GET_INTEGER(v, 3, colnr);
  415. SQ_GET_FLOAT(v, 4, value);
  416. sq_pushbool(v, self->set_mat(self, rownr, colnr, value));
  417. return 1;
  418. }
  419. static SQRESULT sq_lpsolve_solve(HSQUIRRELVM v)
  420. {
  421. SQ_FUNC_VARS_NO_TOP(v);
  422. GET_lpsolve_INSTANCE();
  423. sq_pushinteger(v, self->solve(self));
  424. return 1;
  425. }
  426. static SQRESULT sq_lpsolve_get_objective(HSQUIRRELVM v)
  427. {
  428. SQ_FUNC_VARS_NO_TOP(v);
  429. GET_lpsolve_INSTANCE();
  430. sq_pushfloat(v, self->get_objective(self));
  431. return 1;
  432. }
  433. static SQRESULT sq_lpsolve_get_variables(HSQUIRRELVM v)
  434. {
  435. SQ_FUNC_VARS_NO_TOP(v);
  436. GET_lpsolve_INSTANCE();
  437. const SQInteger ary_idx = 2;
  438. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  439. {
  440. IS_SQFloat64Array(ary_idx);
  441. int ncols = self->get_Ncolumns(self);
  442. if(sq_getsize(v, ary_idx) != ncols) return sq_throwerror(v, _SC("SQFloat64Array of size %d expected"), ncols);
  443. void *ary;
  444. sq_arraygetrawdata(v, ary_idx, &ary);
  445. sq_pushbool(v, self->get_variables(self, (REAL*)ary));
  446. }
  447. else sq_pushbool(v, SQFalse);
  448. return 1;
  449. }
  450. static SQRESULT sq_lpsolve_get_constraints(HSQUIRRELVM v)
  451. {
  452. SQ_FUNC_VARS_NO_TOP(v);
  453. GET_lpsolve_INSTANCE();
  454. const SQInteger ary_idx = 2;
  455. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  456. {
  457. IS_SQFloat64Array(ary_idx);
  458. int nrows = self->get_Nrows(self);
  459. if(sq_getsize(v, ary_idx) != nrows) return sq_throwerror(v, _SC("SQFloat64Array of size %d expected"), nrows);
  460. void *ary;
  461. sq_arraygetrawdata(v, ary_idx, &ary);
  462. sq_pushbool(v, self->get_constraints(self, (REAL*)ary));
  463. }
  464. else sq_pushbool(v, SQFalse);
  465. return 1;
  466. }
  467. static SQRESULT sq_lpsolve_get_dual_solution(HSQUIRRELVM v)
  468. {
  469. SQ_FUNC_VARS_NO_TOP(v);
  470. GET_lpsolve_INSTANCE();
  471. const SQInteger ary_idx = 2;
  472. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  473. {
  474. IS_SQFloat64Array(ary_idx);
  475. int nrows = self->get_Nrows(self);
  476. if(sq_getsize(v, ary_idx) != nrows) return sq_throwerror(v, _SC("SQFloat64Array of size %d expected"), nrows);
  477. void *ary;
  478. sq_arraygetrawdata(v, ary_idx, &ary);
  479. sq_pushbool(v, self->get_dual_solution(self, (REAL*)ary));
  480. }
  481. else sq_pushbool(v, SQFalse);
  482. return 1;
  483. }
  484. static SQRESULT sq_lpsolve_get_sensitivity_obj(HSQUIRRELVM v)
  485. {
  486. SQ_FUNC_VARS_NO_TOP(v);
  487. GET_lpsolve_INSTANCE();
  488. const SQInteger ary_idx_objfrom = 2;
  489. const SQInteger ary_idx_objtill = 3;
  490. IS_SQFloat64Array(ary_idx_objfrom);
  491. IS_SQFloat64Array(ary_idx_objtill);
  492. int nrows = self->get_Nrows(self);
  493. if(sq_getsize(v, ary_idx_objfrom) != nrows || sq_getsize(v, ary_idx_objtill) != nrows)
  494. return sq_throwerror(v, _SC("SQFloat64Array of size %d expected"), nrows);
  495. void *ary_objfrom, *ary_objtill;
  496. sq_arraygetrawdata(v, ary_idx_objfrom, &ary_objfrom);
  497. sq_arraygetrawdata(v, ary_idx_objtill, &ary_objtill);
  498. sq_pushbool(v, self->get_sensitivity_obj(self, (REAL*)ary_objfrom, (REAL*)ary_objtill));
  499. return 1;
  500. }
  501. static SQRESULT sq_lpsolve_get_sensitivity_rhs(HSQUIRRELVM v)
  502. {
  503. SQ_FUNC_VARS_NO_TOP(v);
  504. GET_lpsolve_INSTANCE();
  505. const SQInteger ary_idx_duals = 2;
  506. const SQInteger ary_idx_dualsfrom = 3;
  507. const SQInteger ary_idx_dualstill = 4;
  508. IS_SQFloat64Array(ary_idx_duals);
  509. IS_SQFloat64Array(ary_idx_dualsfrom);
  510. IS_SQFloat64Array(ary_idx_dualstill);
  511. int nrows = self->get_Nrows(self);
  512. if(sq_getsize(v, ary_idx_duals) != nrows || sq_getsize(v, ary_idx_dualsfrom) != nrows || sq_getsize(v, ary_idx_dualstill) != nrows)
  513. return sq_throwerror(v, _SC("SQFloat64Array of size %d expected"), nrows);
  514. void *ary_duals, *ary_dualsfrom, *ary_dualstill;
  515. sq_arraygetrawdata(v, ary_idx_duals, &ary_duals);
  516. sq_arraygetrawdata(v, ary_idx_dualsfrom, &ary_dualsfrom);
  517. sq_arraygetrawdata(v, ary_idx_dualstill, &ary_dualstill);
  518. sq_pushbool(v, self->get_sensitivity_rhs(self, (REAL*)ary_duals, (REAL*)ary_dualsfrom, (REAL*)ary_dualstill));
  519. return 1;
  520. }
  521. static SQRESULT sq_lpsolve_get_nonzeros(HSQUIRRELVM v)
  522. {
  523. SQ_FUNC_VARS_NO_TOP(v);
  524. GET_lpsolve_INSTANCE();
  525. sq_pushinteger(v, self->get_nonzeros(self));
  526. return 1;
  527. }
  528. static SQRESULT sq_lpsolve_get_Nrows(HSQUIRRELVM v)
  529. {
  530. SQ_FUNC_VARS_NO_TOP(v);
  531. GET_lpsolve_INSTANCE();
  532. sq_pushinteger(v, self->get_Nrows(self));
  533. return 1;
  534. }
  535. static SQRESULT sq_lpsolve_get_Ncolumns(HSQUIRRELVM v)
  536. {
  537. SQ_FUNC_VARS_NO_TOP(v);
  538. GET_lpsolve_INSTANCE();
  539. sq_pushinteger(v, self->get_Ncolumns(self));
  540. return 1;
  541. }
  542. static SQRESULT sq_lpsolve_get_status(HSQUIRRELVM v)
  543. {
  544. SQ_FUNC_VARS_NO_TOP(v);
  545. GET_lpsolve_INSTANCE();
  546. sq_pushinteger(v, self->get_status(self));
  547. return 1;
  548. }
  549. static SQRESULT sq_lpsolve_get_statustext(HSQUIRRELVM v)
  550. {
  551. SQ_FUNC_VARS_NO_TOP(v);
  552. GET_lpsolve_INSTANCE();
  553. SQ_GET_INTEGER(v, 2, statuscode);
  554. sq_pushstring(v, self->get_statustext(self, statuscode), -1);
  555. return 1;
  556. }
  557. static SQRESULT sq_lpsolve_get_timeout(HSQUIRRELVM v)
  558. {
  559. SQ_FUNC_VARS_NO_TOP(v);
  560. GET_lpsolve_INSTANCE();
  561. sq_pushinteger(v, self->get_timeout(self));
  562. return 1;
  563. }
  564. static SQRESULT sq_lpsolve_set_timeout(HSQUIRRELVM v)
  565. {
  566. SQ_FUNC_VARS_NO_TOP(v);
  567. GET_lpsolve_INSTANCE();
  568. SQ_GET_INTEGER(v, 2, sectimeout);
  569. self->set_timeout(self, sectimeout);
  570. return 0;
  571. }
  572. static SQRESULT sq_lpsolve_print_lp(HSQUIRRELVM v)
  573. {
  574. SQ_FUNC_VARS_NO_TOP(v);
  575. GET_lpsolve_INSTANCE();
  576. self->print_lp(self);
  577. return 0;
  578. }
  579. static SQRESULT sq_lpsolve_print_objective(HSQUIRRELVM v)
  580. {
  581. SQ_FUNC_VARS_NO_TOP(v);
  582. GET_lpsolve_INSTANCE();
  583. self->print_objective(self);
  584. return 0;
  585. }
  586. static SQRESULT sq_lpsolve_print_solution(HSQUIRRELVM v)
  587. {
  588. SQ_FUNC_VARS_NO_TOP(v);
  589. GET_lpsolve_INSTANCE();
  590. SQ_GET_INTEGER(v, 2, ncols);
  591. self->print_solution(self, ncols);
  592. return 0;
  593. }
  594. static SQRESULT sq_lpsolve_print_constraints(HSQUIRRELVM v)
  595. {
  596. SQ_FUNC_VARS_NO_TOP(v);
  597. GET_lpsolve_INSTANCE();
  598. SQ_GET_INTEGER(v, 2, ncols);
  599. self->print_constraints(self, ncols);
  600. return 0;
  601. }
  602. static SQRESULT sq_lpsolve_print_duals(HSQUIRRELVM v)
  603. {
  604. SQ_FUNC_VARS_NO_TOP(v);
  605. GET_lpsolve_INSTANCE();
  606. self->print_duals(self);
  607. return 0;
  608. }
  609. static SQRESULT sq_lpsolve_set_maxim(HSQUIRRELVM v)
  610. {
  611. SQ_FUNC_VARS_NO_TOP(v);
  612. GET_lpsolve_INSTANCE();
  613. self->set_maxim(self);
  614. return 0;
  615. }
  616. static SQRESULT sq_lpsolve_set_rh(HSQUIRRELVM v)
  617. {
  618. SQ_FUNC_VARS_NO_TOP(v);
  619. GET_lpsolve_INSTANCE();
  620. SQ_GET_INTEGER(v, 2, col);
  621. SQ_GET_FLOAT(v, 3, row);
  622. sq_pushbool(v, self->set_rh(self, col, row));
  623. return 1;
  624. }
  625. static SQRESULT sq_lpsolve_set_rh_range(HSQUIRRELVM v)
  626. {
  627. SQ_FUNC_VARS_NO_TOP(v);
  628. GET_lpsolve_INSTANCE();
  629. SQ_GET_INTEGER(v, 2, col);
  630. SQ_GET_FLOAT(v, 3, row);
  631. sq_pushbool(v, self->set_rh_range(self, col, row));
  632. return 1;
  633. }
  634. static SQRESULT sq_lpsolve_set_binary(HSQUIRRELVM v)
  635. {
  636. SQ_FUNC_VARS_NO_TOP(v);
  637. GET_lpsolve_INSTANCE();
  638. SQ_GET_INTEGER(v, 2, col);
  639. SQ_GET_BOOL(v, 3, bval);
  640. sq_pushbool(v, self->set_binary(self, col, bval));
  641. return 1;
  642. }
  643. static SQRESULT sq_lpsolve_set_int(HSQUIRRELVM v)
  644. {
  645. SQ_FUNC_VARS_NO_TOP(v);
  646. GET_lpsolve_INSTANCE();
  647. SQ_GET_INTEGER(v, 2, col);
  648. SQ_GET_BOOL(v, 3, bval);
  649. sq_pushbool(v, self->set_int(self, col, bval));
  650. return 1;
  651. }
  652. static SQRESULT sq_lpsolve_set_trace(HSQUIRRELVM v)
  653. {
  654. SQ_FUNC_VARS_NO_TOP(v);
  655. GET_lpsolve_INSTANCE();
  656. SQ_GET_BOOL(v, 2, bval);
  657. self->set_trace(self, bval);
  658. return 0;
  659. }
  660. static SQRESULT sq_lpsolve_set_debug(HSQUIRRELVM v)
  661. {
  662. SQ_FUNC_VARS_NO_TOP(v);
  663. GET_lpsolve_INSTANCE();
  664. SQ_GET_BOOL(v, 2, bval);
  665. self->set_debug(self, bval);
  666. return 0;
  667. }
  668. static SQRESULT sq_lpsolve_del_constraint(HSQUIRRELVM v)
  669. {
  670. SQ_FUNC_VARS_NO_TOP(v);
  671. GET_lpsolve_INSTANCE();
  672. SQ_GET_INTEGER(v, 2, cnum);
  673. sq_pushbool(v, self->del_constraint(self, cnum));
  674. return 1;
  675. }
  676. static SQRESULT sq_lpsolve_add_column(HSQUIRRELVM v)
  677. {
  678. SQ_FUNC_VARS_NO_TOP(v);
  679. GET_lpsolve_INSTANCE();
  680. const SQInteger ary_idx = 2;
  681. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  682. {
  683. void *ary;
  684. IS_SQFloat64Array(ary_idx);
  685. sq_arraygetrawdata(v, ary_idx, &ary);
  686. //for(SQInteger i= 0, len =sq_getsize(v, ary_idx); i < len; ++i) printf("add_constraint %d %f\n", (int) i, ((REAL*)ary)[i]);
  687. sq_pushbool(v, self->add_column(self, (REAL*)ary));
  688. }
  689. else sq_pushbool(v, SQFalse);
  690. return 1;
  691. }
  692. static SQRESULT sq_lpsolve_add_columnex(HSQUIRRELVM v)
  693. {
  694. SQ_FUNC_VARS_NO_TOP(v);
  695. GET_lpsolve_INSTANCE();
  696. SQ_GET_INTEGER(v, 2, asize);
  697. const SQInteger ary_row_idx = 3;
  698. const SQInteger ary_col_idx = 4;
  699. if(sq_gettype(v, ary_row_idx) == OT_ARRAY)
  700. {
  701. SQInteger atype;
  702. if(sq_arraygettype(v, ary_row_idx, &atype) != SQ_OK && atype == eat_SQFloat64Array) return sq_throwerror(v, _SC("SQFloat64Array for rows expected"));
  703. if(sq_arraygettype(v, ary_col_idx, &atype) != SQ_OK && atype == eat_SQInt32Array) return sq_throwerror(v, _SC("SQInt32Array for cols expected"));
  704. void *ary_row, *ary_col;
  705. sq_arraygetrawdata(v, ary_row_idx, &ary_row);
  706. sq_arraygetrawdata(v, ary_col_idx, &ary_col);
  707. //for(SQInteger i= 0, len =sq_getsize(v, ary_idx); i < len; ++i) printf("add_constraint %d %f\n", (int) i, ((REAL*)ary)[i]);
  708. sq_pushbool(v, self->add_columnex(self, asize, (REAL*)ary_row, (int*)ary_col));
  709. }
  710. else sq_pushbool(v, SQFalse);
  711. return 1;
  712. }
  713. static SQRESULT sq_lpsolve_set_column(HSQUIRRELVM v)
  714. {
  715. SQ_FUNC_VARS_NO_TOP(v);
  716. GET_lpsolve_INSTANCE();
  717. SQ_GET_INTEGER(v, 2, colno);
  718. const SQInteger ary_idx = 3;
  719. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  720. {
  721. void *ary;
  722. IS_SQFloat64Array(ary_idx);
  723. sq_arraygetrawdata(v, ary_idx, &ary);
  724. //for(SQInteger i= 0, len =sq_getsize(v, ary_idx); i < len; ++i) printf("add_constraint %d %f\n", (int) i, ((REAL*)ary)[i]);
  725. sq_pushbool(v, self->set_column(self, colno, (REAL*)ary));
  726. }
  727. else sq_pushbool(v, SQFalse);
  728. return 1;
  729. }
  730. static SQRESULT sq_lpsolve_set_columnex(HSQUIRRELVM v)
  731. {
  732. SQ_FUNC_VARS_NO_TOP(v);
  733. GET_lpsolve_INSTANCE();
  734. SQ_GET_INTEGER(v, 2, colno);
  735. SQ_GET_INTEGER(v, 3, asize);
  736. const SQInteger ary_row_idx = 4;
  737. const SQInteger ary_col_idx = 5;
  738. if(sq_gettype(v, ary_row_idx) == OT_ARRAY)
  739. {
  740. SQInteger atype;
  741. if(sq_arraygettype(v, ary_row_idx, &atype) != SQ_OK && atype == eat_SQFloat64Array) return sq_throwerror(v, _SC("SQFloat64Array for rows expected"));
  742. if(sq_arraygettype(v, ary_col_idx, &atype) != SQ_OK && atype == eat_SQInt32Array) return sq_throwerror(v, _SC("SQInt32Array for cols expected"));
  743. void *ary_row, *ary_col;
  744. sq_arraygetrawdata(v, ary_row_idx, &ary_row);
  745. sq_arraygetrawdata(v, ary_col_idx, &ary_col);
  746. //for(SQInteger i= 0, len =sq_getsize(v, ary_idx); i < len; ++i) printf("add_constraint %d %f\n", (int) i, ((REAL*)ary)[i]);
  747. sq_pushbool(v, self->set_columnex(self, colno, asize, (REAL*)ary_row, (int*)ary_col));
  748. }
  749. else sq_pushbool(v, SQFalse);
  750. return 1;
  751. }
  752. static SQRESULT sq_lpsolve_del_column(HSQUIRRELVM v)
  753. {
  754. SQ_FUNC_VARS_NO_TOP(v);
  755. GET_lpsolve_INSTANCE();
  756. SQ_GET_INTEGER(v, 2, colno);
  757. sq_pushbool(v, self->del_column(self, colno));
  758. return 1;
  759. }
  760. static SQRESULT sq_lpsolve_get_scaling(HSQUIRRELVM v)
  761. {
  762. SQ_FUNC_VARS_NO_TOP(v);
  763. GET_lpsolve_INSTANCE();
  764. sq_pushinteger(v, self->get_scaling(self));
  765. return 1;
  766. }
  767. static SQRESULT sq_lpsolve_set_scaling(HSQUIRRELVM v)
  768. {
  769. SQ_FUNC_VARS_NO_TOP(v);
  770. GET_lpsolve_INSTANCE();
  771. SQ_GET_INTEGER(v, 2, scal_type);
  772. self->set_scaling(self, scal_type);
  773. return 0;
  774. }
  775. static SQRESULT sq_lpsolve_set_sense(HSQUIRRELVM v)
  776. {
  777. SQ_FUNC_VARS_NO_TOP(v);
  778. GET_lpsolve_INSTANCE();
  779. SQ_GET_BOOL(v, 2, sense_max);
  780. self->set_sense(self, sense_max);
  781. return 0;
  782. }
  783. static SQRESULT sq_lpsolve_unscale(HSQUIRRELVM v)
  784. {
  785. SQ_FUNC_VARS_NO_TOP(v);
  786. GET_lpsolve_INSTANCE();
  787. self->unscale(self);
  788. return 0;
  789. }
  790. static SQRESULT sq_lpsolve_default_basis(HSQUIRRELVM v)
  791. {
  792. SQ_FUNC_VARS_NO_TOP(v);
  793. GET_lpsolve_INSTANCE();
  794. self->default_basis(self);
  795. return 0;
  796. }
  797. static SQRESULT sq_lpsolve_is_presolve(HSQUIRRELVM v)
  798. {
  799. SQ_FUNC_VARS_NO_TOP(v);
  800. GET_lpsolve_INSTANCE();
  801. SQ_GET_INTEGER(v, 2, flags);
  802. sq_pushbool(v, self->is_presolve(self, flags));
  803. return 1;
  804. }
  805. static SQRESULT sq_lpsolve_set_presolve(HSQUIRRELVM v)
  806. {
  807. SQ_FUNC_VARS_NO_TOP(v);
  808. GET_lpsolve_INSTANCE();
  809. SQ_GET_INTEGER(v, 2, flags);
  810. SQ_GET_INTEGER(v, 3, maxloops);
  811. self->set_presolve(self, flags, maxloops);
  812. return 0;
  813. }
  814. static SQRESULT sq_lpsolve_set_constr_type(HSQUIRRELVM v)
  815. {
  816. SQ_FUNC_VARS_NO_TOP(v);
  817. GET_lpsolve_INSTANCE();
  818. SQ_GET_INTEGER(v, 2, rowno);
  819. SQ_GET_INTEGER(v, 3, constraint_type);
  820. sq_pushbool(v, self->set_constr_type(self, rowno, constraint_type));
  821. return 1;
  822. }
  823. static SQRESULT sq_lpsolve_set_row(HSQUIRRELVM v)
  824. {
  825. SQ_FUNC_VARS_NO_TOP(v);
  826. GET_lpsolve_INSTANCE();
  827. SQ_GET_INTEGER(v, 2, rowno);
  828. const SQInteger ary_idx = 3;
  829. if(sq_gettype(v, ary_idx) == OT_ARRAY)
  830. {
  831. void *ary;
  832. IS_SQFloat64Array(ary_idx);
  833. sq_arraygetrawdata(v, ary_idx, &ary);
  834. sq_pushbool(v, self->set_row(self, rowno, (REAL*)ary));
  835. }
  836. else sq_pushbool(v, SQFalse);
  837. return 1;
  838. }
  839. static SQRESULT sq_lpsolve_set_rowex(HSQUIRRELVM v)
  840. {
  841. SQ_FUNC_VARS_NO_TOP(v);
  842. GET_lpsolve_INSTANCE();
  843. SQ_GET_INTEGER(v, 2, rowno);
  844. SQ_GET_INTEGER(v, 3, asize);
  845. const SQInteger ary_row_idx = 4;
  846. const SQInteger ary_col_idx = 5;
  847. if(sq_gettype(v, ary_row_idx) == OT_ARRAY)
  848. {
  849. SQInteger atype;
  850. if(sq_arraygettype(v, ary_row_idx, &atype) != SQ_OK && atype == eat_SQFloat64Array) return sq_throwerror(v, _SC("SQFloat64Array for rows expected"));
  851. if(sq_arraygettype(v, ary_col_idx, &atype) != SQ_OK && atype == eat_SQInt32Array) return sq_throwerror(v, _SC("SQInt32Array for cols expected"));
  852. void *ary_row, *ary_col;
  853. sq_arraygetrawdata(v, ary_row_idx, &ary_row);
  854. sq_arraygetrawdata(v, ary_col_idx, &ary_col);
  855. sq_pushbool(v, self->set_rowex(self, rowno, asize, (REAL*)ary_row, (int*)ary_col));
  856. }
  857. else sq_pushbool(v, SQFalse);
  858. return 1;
  859. }
  860. #define _DECL_FUNC(name,nparams,tycheck) {_SC(#name),sq_lpsolve_##name,nparams,tycheck}
  861. static SQRegFunction sq_lpsolve_methods[] =
  862. {
  863. _DECL_FUNC(constructor,3,_SC(".ii")),
  864. _DECL_FUNC(add_column,2,_SC(".a")),
  865. _DECL_FUNC(add_columnex,4,_SC(".iaa")),
  866. _DECL_FUNC(add_constraint,4,_SC("xain")),
  867. _DECL_FUNC(add_constraintex,6,_SC("xiaain")),
  868. _DECL_FUNC(default_basis,1,_SC(".")),
  869. _DECL_FUNC(del_column,2,_SC(".i")),
  870. _DECL_FUNC(del_constraint,2,_SC(".i")),
  871. _DECL_FUNC(get_col_name,2,_SC("xi")),
  872. _DECL_FUNC(get_constraints,2,_SC("xa")),
  873. _DECL_FUNC(get_dual_solution,2,_SC("xa")),
  874. _DECL_FUNC(get_lp_name,1,_SC("x")),
  875. _DECL_FUNC(get_mat,3,_SC("xii")),
  876. _DECL_FUNC(get_Ncolumns,1,_SC("x")),
  877. _DECL_FUNC(get_nonzeros,1,_SC("x")),
  878. _DECL_FUNC(get_Nrows,1,_SC("x")),
  879. _DECL_FUNC(get_objective,1,_SC("x")),
  880. _DECL_FUNC(get_row_name,2,_SC("xi")),
  881. _DECL_FUNC(get_scaling,1,_SC("x")),
  882. _DECL_FUNC(get_sensitivity_obj,4,_SC("xaa")),
  883. _DECL_FUNC(get_sensitivity_rhs,4,_SC("xaaa")),
  884. _DECL_FUNC(get_statustext,2,_SC("xi")),
  885. _DECL_FUNC(get_status,1,_SC("x")),
  886. _DECL_FUNC(get_timeout,1,_SC("x")),
  887. _DECL_FUNC(get_variables,2,_SC("xa")),
  888. _DECL_FUNC(is_presolve,2,_SC(".i")),
  889. _DECL_FUNC(loadlib,2,_SC(".s")),
  890. _DECL_FUNC(print_constraints,2,_SC(".i")),
  891. _DECL_FUNC(print_duals,1,_SC(".")),
  892. _DECL_FUNC(print_lp,1,_SC(".")),
  893. _DECL_FUNC(print_objective,1,_SC(".")),
  894. _DECL_FUNC(print_solution,2,_SC(".i")),
  895. _DECL_FUNC(read_basis,2,_SC(".s")),
  896. _DECL_FUNC(read_freeMPS,3,_SC(".si")),
  897. _DECL_FUNC(read_LP,4,_SC(".sbs")),
  898. _DECL_FUNC(read_MPS,3,_SC(".si")),
  899. _DECL_FUNC(read_params,3,_SC("xss")),
  900. _DECL_FUNC(resize_lp,3,_SC(".ii")),
  901. _DECL_FUNC(set_binary,3,_SC(".ib")),
  902. _DECL_FUNC(set_bounds,4,_SC("xinn")),
  903. _DECL_FUNC(set_col_name,3,_SC("xis")),
  904. _DECL_FUNC(set_column,3,_SC(".ia")),
  905. _DECL_FUNC(set_columnex,5,_SC(".iiaa")),
  906. _DECL_FUNC(set_constr_type,3,_SC(".ii")),
  907. _DECL_FUNC(set_debug,2,_SC(".b")),
  908. _DECL_FUNC(set_int,3,_SC(".ib")),
  909. _DECL_FUNC(set_lowbo,3,_SC("xin")),
  910. _DECL_FUNC(set_lp_name,2,_SC("xs")),
  911. _DECL_FUNC(set_mat,4,_SC("xiin")),
  912. _DECL_FUNC(set_maxim,1,_SC(".")),
  913. _DECL_FUNC(set_obj_fn,2,_SC("xa")),
  914. _DECL_FUNC(set_presolve,3,_SC(".ii")),
  915. _DECL_FUNC(set_rh,3,_SC(".in")),
  916. _DECL_FUNC(set_rh_range,3,_SC(".in")),
  917. _DECL_FUNC(set_row,3,_SC(".ia")),
  918. _DECL_FUNC(set_rowex,5,_SC(".iiaa")),
  919. _DECL_FUNC(set_row_name,3,_SC("xis")),
  920. _DECL_FUNC(set_scaling,2,_SC(".i")),
  921. _DECL_FUNC(set_sense,2,_SC(".b")),
  922. _DECL_FUNC(set_timeout,2,_SC("xi")),
  923. _DECL_FUNC(set_trace,2,_SC(".b")),
  924. _DECL_FUNC(set_upbo,3,_SC("xin")),
  925. _DECL_FUNC(set_verbose,2,_SC("xi")),
  926. _DECL_FUNC(solve,1,_SC("x")),
  927. _DECL_FUNC(unscale,1,_SC(".")),
  928. _DECL_FUNC(version,1,_SC(".")),
  929. _DECL_FUNC(write_basis,2,_SC("xs")),
  930. _DECL_FUNC(write_freemps,2,_SC("xs")),
  931. _DECL_FUNC(write_lp,2,_SC("xs")),
  932. _DECL_FUNC(write_mps,2,_SC("xs")),
  933. _DECL_FUNC(write_params,3,_SC("xss")),
  934. {0,0}
  935. };
  936. #undef _DECL_FUNC
  937. typedef struct {
  938. const SQChar *Str;
  939. SQInteger Val;
  940. } KeyIntType, * KeyIntPtrType;
  941. static KeyIntType lpsolve_constants[] = {
  942. #define MK_CONST(c) {_SC(#c), c}
  943. MK_CONST(NEUTRAL),
  944. MK_CONST(CRITICAL),
  945. MK_CONST(SEVERE),
  946. MK_CONST(IMPORTANT),
  947. MK_CONST(NORMAL),
  948. MK_CONST(DETAILED),
  949. MK_CONST(FULL),
  950. MK_CONST(SCALE_NONE),
  951. MK_CONST(SCALE_EXTREME),
  952. MK_CONST(SCALE_RANGE),
  953. MK_CONST(SCALE_MEAN),
  954. MK_CONST(SCALE_GEOMETRIC),
  955. MK_CONST(SCALE_FUTURE1),
  956. MK_CONST(SCALE_FUTURE2),
  957. MK_CONST(SCALE_CURTISREID),
  958. MK_CONST(SCALE_LINEAR),
  959. MK_CONST(SCALE_QUADRATIC),
  960. MK_CONST(SCALE_LOGARITHMIC),
  961. MK_CONST(SCALE_USERWEIGHT),
  962. MK_CONST(SCALE_MAXTYPE),
  963. MK_CONST(SCALE_POWER2),
  964. MK_CONST(SCALE_EQUILIBRATE),
  965. MK_CONST(SCALE_INTEGERS),
  966. MK_CONST(SCALE_DYNUPDATE),
  967. MK_CONST(SCALE_ROWSONLY),
  968. MK_CONST(SCALE_COLSONLY),
  969. MK_CONST(SCALEMODEL_EQUILIBRATED),
  970. MK_CONST(SCALEMODEL_GEOMETRIC),
  971. MK_CONST(SCALEMODEL_ARITHMETIC),
  972. MK_CONST(SCALEMODEL_DYNAMIC),
  973. MK_CONST(SCALEMODEL_CURTISREID),
  974. /* Presolve defines */
  975. MK_CONST(PRESOLVE_NONE),
  976. MK_CONST(PRESOLVE_ROWS),
  977. MK_CONST(PRESOLVE_COLS),
  978. MK_CONST(PRESOLVE_LINDEP),
  979. MK_CONST(PRESOLVE_AGGREGATE),
  980. MK_CONST(PRESOLVE_SPARSER),
  981. MK_CONST(PRESOLVE_SOS),
  982. MK_CONST(PRESOLVE_REDUCEMIP),
  983. MK_CONST(PRESOLVE_KNAPSACK),
  984. MK_CONST(PRESOLVE_ELIMEQ2),
  985. MK_CONST(PRESOLVE_IMPLIEDFREE),
  986. MK_CONST(PRESOLVE_REDUCEGCD),
  987. MK_CONST(PRESOLVE_PROBEFIX),
  988. MK_CONST(PRESOLVE_PROBEREDUCE),
  989. MK_CONST(PRESOLVE_ROWDOMINATE),
  990. MK_CONST(PRESOLVE_COLDOMINATE),
  991. MK_CONST(PRESOLVE_MERGEROWS),
  992. MK_CONST(PRESOLVE_IMPLIEDSLK),
  993. MK_CONST(PRESOLVE_COLFIXDUAL),
  994. MK_CONST(PRESOLVE_BOUNDS),
  995. MK_CONST(PRESOLVE_LASTMASKMODE),
  996. MK_CONST(PRESOLVE_DUALS),
  997. MK_CONST(PRESOLVE_SENSDUALS),
  998. MK_CONST(FR),
  999. MK_CONST(LE),
  1000. MK_CONST(GE),
  1001. MK_CONST(EQ),
  1002. MK_CONST(OF),
  1003. {0,0}
  1004. };
  1005. #ifdef __cplusplus
  1006. extern "C" {
  1007. #endif
  1008. SQRESULT sqext_register_lpsolve(HSQUIRRELVM v)
  1009. {
  1010. sq_pushstring(v,LPSOLVE_Tag,-1);
  1011. sq_newclass(v,SQFalse);
  1012. sq_settypetag(v,-1,(SQUserPointer)LPSOLVE_Tag);
  1013. sq_insert_reg_funcs(v, sq_lpsolve_methods);
  1014. //add constants
  1015. KeyIntPtrType KeyIntPtr;
  1016. for (KeyIntPtr = lpsolve_constants; KeyIntPtr->Str; KeyIntPtr++) {
  1017. sq_pushstring(v, KeyIntPtr->Str, -1); //first the key
  1018. sq_pushinteger(v, KeyIntPtr->Val); //then the value
  1019. sq_newslot(v, -3, SQTrue); //store then
  1020. }
  1021. sq_newslot(v,-3,SQTrue);
  1022. return 0;
  1023. }
  1024. #ifdef __cplusplus
  1025. }
  1026. #endif
  1027. #endif //SQ_USE_LPSOLVE