I understand that Z3 has some supports for nonlinear arith but wondering to what extends ? Is it possible to specify what classes of nonlinear arithmetics are supported and are not (or likely to give time out) ? Know these in advances will help me abort my task early.
Seems like power related stuff is not supported as shown below
def pow2(x):
k=Int('k')
return Exists(k, And(k>=0,2**k==x))
prove(pow2(7))
failed to prove
Z3 supports nonlinear polynomial Real arithmetic. So, there is no support for transcendental functions (e.g., sine and cosine), and exponential (e.g., 2^x). Actually, for the exponential, Z3 can handle exponents that can be simplified to numerals. Here is an example,
x = Real('x')
y = Real('y')
solve(y == 3, x**y == 2)
In this example, the y in x**y is rewritten to 3 during a preprocessing step. After preprocessing, the nlsat solver for nonlinear polynomial real arithmetic is invoked.
Regarding nonlinear integer arithmetic, see this related post.
Related
Is it possible to extract the upper and (or) lower bound of some numerical variables in Z3? Suppose there are some constraints on numerical variable x, and the cause of the constraints is that x must be in the interval [x_min, x_max]. Is there a way in Z3 to extract these bounds (x_min and x_max) (in case the solver calculates these values internally), without doing optimization (minimization and maximization).
You could try to increase Z3's verbosity, maybe you can find bounds in the output.
I doubt it, though: since Z3 is ultimately a SAT solver, any numerical solver that (tries to) decide satisfiability could be applied, but deciding satisfiability doesn't necessary require computing (reasonable) numerical bounds.
Out of curiosity: why would you like to avoid optimisation queries?
In general, no.
The minimum/maximum optimal values of a variable x provide the tightest over-approximation of the satisfiable domain interval of x. This requires enumerating all possible Boolean assignments, not just one.
The (Dual) Simplex Algorithm inside the T-Solver for linear arithmetic keeps track of bounds for all arithmetic variables. However, these bounds are only valid for the (possibly partial) Boolean assignment that is currently being constructed by the SAT engine. In early pruning calls, there is no guarantee whatsoever about the significance of these bounds: the corresponding domain for a given variable x may be an under-approximation, an over-approximation or neither (compared to the domain of x wrt. the input formula).
The Theory Combination approach implemented by a SMT solver can also affect the significance of the bounds available inside the LA-Solver. In this regard, I can vouch that Model-Based Theory Combination can be particularly nasty to deal with. With this approach, the SMT Solver may not generate some interface equalities/inequalities when the T-Solvers agree on the Model Value of an interface variable. However, this is counterproductive when one wants to know from the LA-Solver the valid domain of a variable x because it can provide an over-approximated interval even after finding a model of the input formula for a given total Boolean assignment.
Unless the original problem --after preprocessing-- contains terms of the form (x [<|<=|=|=>|>] K), for all possibly interesting values of K, it is hardly likely that the SMT solver generates any valid T-lemma of this form during the search. The main exception is when x is an Int and the LIA-Solver uses splitting on demand. As a consequence, the Boolean stack is not that much helpful to discover bounds either and, even if they were generated, they would only provide an under-approximation of the feasible interval of x (when they are contained in a satisfiable total Boolean assignment).
I've come up with an SMT formula in Z3 which outputs one solution to a constraint solving problem using only BitVectors and IntVectors of fixed length. The logic I use for the IntVectors is only simple Presburger arithmetic (of the form (x[i] - x[i + 1] <=/>= z) for some x and z). I also take the sum of all of the bits in the bitvector (NOT the binary value), and set that value to be within a range of [a, b].
This works perfectly. The only problem is that, as z3 works by always taking the easiest path towards determining satisfiability, I always get the same answer back, whereas in my domain I'd like to find a variety of substantially different solutions (I know for a fact that multiple, very different solutions exist). I'd like to use this nifty tool I found https://bitbucket.org/kuldeepmeel/weightgen, which lets you uniformly sample a constrained space of possibilities using SAT. To use this though, I need to convert my SMT formula into a SAT formula.
Do you know of any resources that would help me learn how to perform Presburger arithmetic and adding the bits of a bitvector as a SAT instance? Alternatively, do you know of any SMT solver which as an intermediate step outputs a readable description of the problem as a SAT instance?
Many thanks!
[Edited to reflect the fact that I really do need the uniform sampling feature.]
I would like to prove properties of expressions involving matrices and vectors (potentially large size, but size is fixed).
For example I want to prove that the outcome of an expression is a diagonal matrix or a triangular matrix, or it is positive definite, ...
To that end I'd like encode well known properties and identities from linear algebra, such as:
||x + y|| <= ||x|| + ||y||
(A * B) * C = A * (B * C)
det(A+B) = det(A) + det(B)
Tr(zA) = z * Tr(A)
(I + AB) ^ (-1) = I - A(I + BA) ^ (-1) * B
...
I have attempted to implement this in Z3. But even for simple properties it returns unknown or times out. I've tried with array theory and quantifiers.
I'd like know if this problem can be solved with an SMT solver or is it not suited for these kind of problems? Could you give a hint by giving a small example?
You can certainly use Z3 to do this.
I have constructed a small example here, which defines the identity matrix and what it means to be a diagonal matrix, and then proves that the identity matrix is diagonal.
So, it is definitely possible to do this kind of work in Z3. Though you may find you have a better time using a tool built on top of Z3 that has more interactive proving features, such as Dafny or F*.
I'm using Z3 to solve a system that consists of Boolean constraints on variables Vi as well as a constraint of the following form:
L < If(V0, T0, F0) + If(V1, T1, F1) + ... + If(Vn, Tn, Fn) <= H
where L, H, and the Ti and Fi are integer constants.
Although all the variables are Boolean, I found that the QF_LIA solver was somewhat faster than the generic one, so I'm using the former. My assumption was that Z3 was handling the constraint above by introducing new variables and clauses to implement adders in the obvious way. However, doing that conversion myself (using MiniSat+) and passing the result to a SAT solver takes an order of magnitude longer than Z3 does. Thus, I'm wondering what strategy Z3 uses to solve systems of the type described above - is it something other than the conversion using adders?
Z3 uses a reduction to SAT to solve this kind of problem. If you are using the shell, you can provide the option -v:10 (verbosity messages). Z3 will display several messages describing what it is doing. For the kind of problem you described, Z3 will probably display verbose messages of the form:
(lia2pb :num-exprs 9 :num-asts 185 ...)
(pb2bv :num-exprs 9 :num-asts 185 ...)
lia2pb means that Z3 is converting a linear integer arithmetic problem into a pseudo boolean constraint problem. And pb2bv means that it is reducing the problem to bit-vector arithmetic.
The lia2pb transformation is implemented in the file:
http://z3.codeplex.com/SourceControl/latest#src/tactic/arith/lia2pb_tactic.cpp
and pb2bv transformation is implemented in the file:
http://z3.codeplex.com/SourceControl/latest#src/tactic/arith/pb2bv_tactic.cpp
Many thanks Josh and Leonardo for answering the previous question.
I have few more questions.
<1> Consider another example.
(exists k) i * k > = 4 and k > 1.
This has a simple solution i > 0. (both for Int and Real case)
However, when I tried following,
(declare-const i Int)
(assert (exists ((k Int)) (and (>= (* i k) 4) (> k 1))))
(apply (using-params qe :qe-nonlinear true))
Z3 Could not eliminate quantifier here.
However, it could eliminate for a Real case. (when i and k are both reals)
Is Quantifier Elimination more difficult for integers?
<2> I am using Z3 C API in my system. I am adding some non-linear constraints on Integers with quantifiers in my system.
Z3 currently checks for satisfiability and gives me a correct model when the system is satisfiable.
I know that after quantifier elimination, these constraints get reduced to linear constraints.
I thought that z3 does quantifier elimination automatically before checking satisfiability. But since, it couldn't do that in case 1 above, I now think, that it usually finds a model without Quantifier Elimination. Am I correct?
Currently z3 can solve the constraints in my system. But it may fail on complex systems.
In such case, is it a good idea to do quantifier elimination by some other method without z3 and add constraints to z3 later?
<3> I can think of adding Real non-linear constraints instead of Integer non-linear constraints in my system. In that case, how can I enforce z3 to do Quantifier Elimination using C-API ?
<4> Finally, is this a good idea to enforce z3 to do Quantifier Elimination? Or it usually finds a model more intelligently without doing Quantifier Elimination?
Thanks.
<1> The theory of nonlinear integer arithmetic does not admit quantifier elimination (qe).
Moreover, the decision problem for nonlinear integer arithmetic is undecidable.
Recall that, Z3 has limited support for quantifier elimination of nonlinear real arithmetic formulas. The current procedure is based on virtual term substitution. Future versions, may have full support for nonlinear real arithmetic.
<2> Quantifier elimination is not enabled by default. The user must request it.
Z3 may find models for satisfiable formulas even when quantifier elimination is not enabled.
It uses a technique called model-based quantifier instantiation (MBQI). The Z3 online tutorial has several examples describing capabilities and limitations of this technique.
<3> You have to enable it when you create the Z3_context object.
Any option that is set in the command line, can be provided during Z3_context object creation. Here is an example, that enables model construction and quantifier elimination:
Z3_config cfg = Z3_mk_config();
Z3_context ctx;
Z3_set_param_value(cfg, "MODEL", "true");
Z3_set_param_value(cfg, "ELIM_QUANTIFIERS", "true");
Z3_set_param_value(cfg, "ELIM_NLARITH_QUANTIFIERS", "true");
ctx = mk_context_custom(cfg, throw_z3_error);
Z3_del_config(cfg);
After that, ctx is pointing to a Z3 context object that supports model construction and quantifier elimination.
<4> The MBQI module is not complete even for the linear arithmetic fragment.
The Z3 online tutorial describes the fragments it is complete. MBQI module is a good option for problems that contain uninterpreted functions. If your problems only use arithmetic, then quantifier elimination is usually better and more efficient. That being said, several problems can be quickly solved using MBQI.