def test_is_not_predicate(): context = Context() @context.valasp(validate_predicate=False) class Month: value: int def __post_init__(self): if not (1 <= self.value <= 12): raise ValueError('month not in 1..12') assert str(Month(Number(1))) == 'Month(1)' with pytest.raises(ValueError): Month(Number(0)) with pytest.raises(TypeError): Month(QString('Sep')) @context.valasp(with_fun=Fun.TUPLE) class Salary: amount: Integer month: Month assert str(Salary(Tuple([Number(1000), Number(1)]))) == 'Salary(1000,Month(1))' with pytest.raises(ValueError): Salary(Tuple([Number(1000), Number(13)])) with pytest.raises(TypeError): Salary(Tuple([Number(1000), QString('Jan')]))
def test_complex_implicit_no_predicate(): context = Context() @context.valasp(validate_predicate=False) class Date: year: int month: int day: int def __post_init__(self): datetime.datetime(self.year, self.month, self.day) @context.valasp(with_fun=Fun.TUPLE) class Birthday: name: String date: Date assert str(Date(Function( 'date', [Number(1983), Number(9), Number(12)]))) == 'Date(1983,9,12)' with pytest.raises(TypeError): Date(Number(1983), Number(9), Number(12)) with pytest.raises(ValueError): Date(Tuple([Number(1983), Number(9), Number(12)])) with pytest.raises(ValueError): Date(Function('date', [Number(1983), Number(9)])) with pytest.raises(ValueError): Date(Function('data', [Number(1983), Number(9), Number(12)])) date = Function('date', [Number(1983), Number(9), Number(12)]) assert str(Birthday(Tuple([QString('mario'), date]))) == 'Birthday(mario,Date(1983,9,12))' with pytest.raises(TypeError): Birthday(QString('mario'), Number(0))
def _weight_rule(self, choice, head, lower_bound, body): head = sorted(set([self._map(atm) for atm in head])) body = sorted( set([Tuple([self._map(lit), weight]) for lit, weight in body])) self._reified.append( Function("weight_rule", [choice, Tuple(head), lower_bound, Tuple(body)]))
def _theory_atom_with_guard(self, atom_id_or_zero, term_id, elements, operator_id, right_hand_side_id): self._symbols[atom_id_or_zero] = Function("theory", [ self._terms[term_id](), Tuple(sorted(set([self._elems[e]() for e in elements]))), self._terms[operator_id](), self._terms[right_hand_side_id]() ])
def test_auto_blacklist(): context = Context() @context.valasp(with_fun=Fun.TUPLE) class Edge: source: Integer dest: Integer Edge(Tuple([Number(1), Number(2)])) assert str(context.valasp_run_solver(["edge(1,2)."])) == '[edge(1,2)]' with pytest.raises(RuntimeError): context.valasp_run_solver(["edge(1,2). edge((1,2))."])
def test_date_as_tuple(): context = Context() @context.valasp(validate_predicate=False, with_fun=Fun.TUPLE) class Date: year: int month: int day: int def __post_init__(self): datetime.datetime(self.year, self.month, self.day) @context.valasp() class Birthday: name: str date: Date Birthday( Function( 'birthday', [QString('mario'), Tuple([Number(1983), Number(9), Number(12)])])) model = context.valasp_run_solver(['birthday("sofia", (2019,6,25)).']) assert str(model) == '[birthday("sofia",(2019,6,25))]' model = context.valasp_run_solver([ 'birthday("sofia", (2019,6,25)).', 'birthday("leonardo", (2018,2,1)).' ]) assert str( model ) == '[birthday("sofia",(2019,6,25)), birthday("leonardo",(2018,2,1))]' with pytest.raises(RuntimeError): context.valasp_run_solver(['birthday("bigel", (1982,123)).']) with pytest.raises(RuntimeError): context.valasp_run_solver(['birthday("no one", (2019,2,29)).']) with pytest.raises(RuntimeError): context.valasp_run_solver(['birthday("sofia", date(2019,6,25)).'])
def test_complex_type(): context = Context() @context.valasp() class Node: value: Integer @context.valasp(with_fun=Fun.TUPLE) class Edge: from_: Node to: Node def check_ordered(self): if not (self.from_ < self.to): raise ValueError("nodes must be ordered") Edge(Tuple([Number(1), Number(2)])) model = context.valasp_run_solver(['node(1). node(2). edge(1,2).']) assert str(model) == '[node(1), node(2), edge(1,2)]' with pytest.raises(RuntimeError): context.valasp_run_solver(['node(1). node(2). edge(2,1).'])
def _output_csp(self, symbol, value, condition): condition = sorted(set([self._map(lit) for lit in condition])) self._reified.append( Function("output_csp", [symbol, value, Tuple(condition)]))
def _theory_atom(self, atom_id_or_zero, term_id, elements): self._symbols[atom_id_or_zero] = Function("theory", [ self._terms[term_id](), Tuple(sorted(set([self._elems[e]() for e in elements]))) ])
def theory_element(self, element_id, terms, condition): self._elems[element_id] = lambda: Function("elem", [ Tuple([self._terms[i]() for i in terms]), Tuple(sorted(set([self._map(lit) for lit in condition]))) ])
def _acyc_edge(self, node_u, node_v, condition): condition = sorted(set([self._map(lit) for lit in condition])) self._reified.append( Function("acyc_edge", [node_u, node_v, Tuple(condition)]))
def _heuristic(self, atom, type, bias, priority, condition): condition = sorted(set([self._map(lit) for lit in condition])) self._reified.append( Function("heuristic", [atom, str(type), bias, Tuple(condition)]))
def _assume(self, literals): literals = sorted(set([self._map(lit) for lit in literals])) self._reified.append(Function("assume", [Tuple(literals)]))
def _project(self, atoms): atoms = sorted(set([self._map(atm) for atm in atoms])) self._reified.append(Function("project", [Tuple(atoms)]))
def _minimize(self, priority, literals): literals = sorted( set([Tuple([self._map(lit), weight]) for lit, weight in literals])) self._reified.append(Function("minimize", [priority, Tuple(literals)]))
def _rule(self, choice, head, body): head = sorted(set([self._map(atm) for atm in head])) body = sorted(set([self._map(lit) for lit in body])) self._reified.append( Function("rule", [choice, Tuple(head), Tuple(body)]))