1
0
This repository has been archived on 2025-03-06. You can view files and clone it, but cannot push or open issues or pull requests.
Jip J. Dekker f2a1c4e389 Squashed 'software/mza/' content from commit f970a59b17
git-subtree-dir: software/mza
git-subtree-split: f970a59b177c13ca3dd8aaef8cc6681d83b7e813
2021-07-11 16:34:30 +10:00

195 lines
8.9 KiB
C

/*
* Author:
* Tai Tran <tai.tran@student.adelaide.edu.au>
* Supervisor:
* Guido Tack <guido.tack@monash.edu>
*/
#ifndef __MODEL_H
#define __MODEL_H
#include "global.h"
struct MznModel {
PyObject_HEAD Env* _e;
Model* _m;
vector<string>* includePaths;
// SolverCode definition is in global.h
enum SolverCode { SC_UNKNOWN, SC_GECODE } sc;
const static SolverCode default_solver = SC_UNKNOWN;
unsigned long timeLimit;
bool loaded;
MznModel();
int load(PyObject* args, PyObject* keywds, bool fromFile);
int addData(const char* const name, PyObject* value);
PyObject* set_solver(const char* s);
PyObject* solve(PyObject* args, PyObject* kwds);
};
void MznModelDestructor(PyObject* o);
static PyObject* MznModel_new(PyTypeObject* type, PyObject* args, PyObject* kwds);
static int MznModel_init(MznModel* self, PyObject* args);
static void MznModel_dealloc(MznModel* self);
/************************************************************
Groups of function general functions
************************************************************/
/** Function arguments - allow keywords
dict: dictionary of name - value, used when loading from a minizinc file only
key: name of the value to be assigned
value: value to be assigned
solver: solver name
if solver_name == '', do nothing
else, solve the model using specified solver
time: time limit
if time_limit != 0, set new time limit
*/
static PyObject* MznModel_solve(MznModel* self, PyObject* args, PyObject* kwds);
static PyObject* MznModel_set_time_limit(MznModel* self, PyObject* args);
static PyObject* MznModel_set_solver(MznModel* self, PyObject* args);
/************************************************************
Groups of function functions to interact with MiniZinc files
************************************************************/
static PyObject* MznModel_load(MznModel* self, PyObject* args, PyObject* keywds);
static PyObject* MznModel_load_from_string(MznModel* self, PyObject* args, PyObject* keywds);
// Take in a name and a Python value, add that data to the current model
static PyObject* MznModel_addData(MznModel* self, PyObject* args);
/***************************************************************
Groups of function functions to interact with Python Interface
***************************************************************/
/* Function: MznModel_Declaration
* Description: Take in a tuple of arguments, create a Variable in the Minizinc Model self
* Arguments:
* 1: name, TypeId, dimension vector, lower bound, upper bound
* name: string
* TypeId: see enum TypeId below
* dimension vector: empty if Variable is not an array
* holds value if it is an array
* Syntax: vector<pair<int, int> >, called dimList
* - dimList[i] is the lower bound and upper bound of dimension i
* - for example:
* dimList[0] = <1,5>
* dimList[1] = <2,4>
* dimList[2] = <0,5>
* means a 3d array [1..5,2..4,0..5]
* lower bound: can be MiniZinc Set, int or float
* upper bound: None if lower bound is MiniZinc Set,
* type(lower bound) otherwise
*
* 2: name, python value
* python value: Create a variable based on the existing python value
* Return:
* Id of the declared variable
* Note 1:
* Don't reuse this declaration if the model with this declaration has been destroyed
* Note 2:
* Python Interface holds the responsibility of checking which type of value is declared.
*/
static PyObject* MznModel_Declaration(MznModel* self, PyObject* args);
/* Function: MznModel_Constraint
* Description: Take in a Python boolean or MiniZinc Expression, add it to the MiniZinc Model self
* Return:
* None
* Note: It is the Python Interface responsibility to check if parsed argument is of type bool or
* not
*/
static PyObject* MznModel_Constraint(MznModel* self, PyObject* args);
/* Function: MznModel_SolveItem
* Description: Add a solve item into the model
* Arguments:
* Arg1: Solve Type: 0 ~ sat, 1 ~ min, 2 ~ max
* Arg2 (opt): Annotation
* Arg3 (opt): Expression to be minimize / maximize if Arg1 != 0
* Return:
* None
* Note:
* Arg2 accepts all MiniZinc expression, but the Python Interface should ensures that
* Arg2 is an expression of MiniZinc Annotation.
*/
static PyObject* MznModel_SolveItem(MznModel* self, PyObject* args);
// Returns an exact copy of the current model
static PyObject* MznModel_copy(MznModel* self);
// Print the MiniZinc representation of the model
static PyObject* MznModel_debugprint(MznModel* self);
// Declare all the functions
static PyMethodDef MznModel_methods[] = {
{"load", (PyCFunction)MznModel_load, METH_KEYWORDS, "Load MiniZinc model from MiniZinc file"},
{"load_from_string", (PyCFunction)MznModel_load_from_string, METH_KEYWORDS,
"Load MiniZinc model from standard input"},
{"addData", (PyCFunction)MznModel_addData, METH_VARARGS, "Add data to a MiniZinc model"},
{"solve", (PyCFunction)MznModel_solve, METH_VARARGS | METH_KEYWORDS,
"Solve a loaded MiniZinc model"},
{"set_time_limit", (PyCFunction)MznModel_set_time_limit, METH_VARARGS,
"Limit the execution time of the model"},
{"set_solver", (PyCFunction)MznModel_set_solver, METH_VARARGS,
"Choose which model will be used to solve the model"},
{"Declaration", (PyCFunction)MznModel_Declaration, METH_VARARGS,
"Add a variable into the model"},
{"Constraint", (PyCFunction)MznModel_Constraint, METH_VARARGS,
"Add a constraint into the model"},
{"SolveItem", (PyCFunction)MznModel_SolveItem, METH_VARARGS, "Add a solve item into the model"},
{"copy", (PyCFunction)MznModel_copy, METH_NOARGS, "Returns a copy of current model"},
{"debugprint", (PyCFunction)MznModel_debugprint, METH_NOARGS,
"Print the MiniZinc representation of the current model"},
{NULL} /* Sentinel */
};
static PyMemberDef MznModel_members[] = {
{NULL} /* Sentinel */
};
static PyTypeObject MznModel_Type = {
PyVarObject_HEAD_INIT(NULL, 0) "minizinc_internal.Model", /* tp_name */
sizeof(MznModel), /* tp_basicsize */
0, /* tp_itemsize */
(destructor)MznModel_dealloc, /* tp_dealloc */
0, /* tp_print */
0, /* tp_getattr */
0, /* tp_setattr */
0, /* tp_reserved */
0, /* tp_repr */
0, /* tp_as_number */
0, /* tp_as_sequence */
0, /* tp_as_mapping */
0, /* tp_hash */
0, /* tp_call */
0, /* tp_str */
0, /* tp_getattro */
0, /* tp_setattro */
0, /* tp_as_buffer */
Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */
"Minizinc Model", /* tp_doc */
0, /* tp_traverse */
0, /* tp_clear */
0, /* tp_richcompare */
0, /* tp_weaklistoffset */
0, /* tp_iter */
0, /* tp_iternext */
MznModel_methods, /* tp_methods */
MznModel_members, /* tp_members */
0, /* tp_getset */
0, /* tp_base */
0, /* tp_dict */
0, /* tp_descr_get */
0, /* tp_descr_set */
0, /* tp_dictoffset */
(initproc)MznModel_init, /* tp_init */
0, /* tp_alloc */
MznModel_new, /* tp_new */
};
#endif