I have a program that generates a set of constraints in nonlinear real arithmetic. Consider the following two constraints:
(< (- (- (- (+ (* (- v0_x v3_x) (- v1_y v3_y) (+ (* (- v2_x v3_x) (- v2_x v3_x)) (* (- v2_y v3_y) (- v2_y v3_y)))) (* (- v0_y v3_y) (- v2_x v3_x) (+ (* (- v1_x v3_x) (- v1_x v3_x)) (* (- v1_y v3_y) (- v1_y v3_y)))) (* (- v1_x v3_x) (- v2_y v3_y) (+ (* (- v0_x v3_x) (- v0_x v3_x)) (* (- v0_y v3_y) (- v0_y v3_y))))) (* (- v1_y v3_y) (- v2_x v3_x) (+ (* (- v0_x v3_x) (- v0_x v3_x)) (* (- v0_y v3_y) (- v0_y v3_y))))) (* (- v0_y v3_y) (- v1_x v3_x) (+ (* (- v2_x v3_x) (- v2_x v3_x)) (* (- v2_y v3_y) (- v2_y v3_y))))) (* (- v0_x v3_x) (- v2_y v3_y) (+ (* (- v1_x v3_x) (- v1_x v3_x)) (* (- v1_y v3_y) (- v1_y v3_y))))) 0)
(> (- (- (- (+ (* (- v0_x v2_x) (- v1_y v2_y) (+ (* (- v3_x v2_x) (- v3_x v2_x)) (* (- v3_y v2_y) (- v3_y v2_y)))) (* (- v0_y v2_y) (- v3_x v2_x) (+ (* (- v1_x v2_x) (- v1_x v2_x)) (* (- v1_y v2_y) (- v1_y v2_y)))) (* (- v1_x v2_x) (- v3_y v2_y) (+ (* (- v0_x v2_x) (- v0_x v2_x)) (* (- v0_y v2_y) (- v0_y v2_y))))) (* (- v1_y v2_y) (- v3_x v2_x) (+ (* (- v0_x v2_x) (- v0_x v2_x)) (* (- v0_y v2_y) (- v0_y v2_y))))) (* (- v0_y v2_y) (- v1_x v2_x) (+ (* (- v3_x v2_x) (- v3_x v2_x)) (* (- v3_y v2_y) (- v3_y v2_y))))) (* (- v0_x v2_x) (- v3_y v2_y) (+ (* (- v1_x v2_x) (- v1_x v2_x)) (* (- v1_y v2_y) (- v1_y v2_y))))) 0)
when I assert them to Z3, it says that it is satisfiable, but as soon as I change the second constraint to (< ... 0) instead of (> ... 0) which should be now unsatisfiable, z3 runs forever. I am wondering about the limitations of z3 for handing nonlinear real arithmetic. Is there any chance that Z3 can handle the above constraints (like by changing the way they are formulated or any other way)?
Yes, when we change
(< ... 0)
to(> ... 0)
the problem becomes unsatisfiable, and there is a trivial proof for that since it becomesp < 0 and p > 0
. The two polynomials in your post are identical after simplifications. However, Z3 misses this simple proof. This is be fixed in the next releases. In the meantime, we can catch examples that have this kind of simple proof by using a custom strategy.This strategy does the polynomial normalization and calls an engine that detects the inconsistency in
p < 0
andp > 0
. The whole example is available online at: http://rise4fun.com/Z3/JP4. I also pasted it in the end of the message.Z3 keeps running forever because it misses the short/easy proof and tries to find the proof using more expensive and complete methods. The algorithm used by Z3 is described here. The algorithm uses a projection operator based on subresultants. This operation is very expensive, and produces very big polynomials for your example. This procedure works well for problems containing small polynomials with a small set of variables on each of them. In the future, we plan to combine complete and incomplete techniques and improve the set of problems that Z3 can solve in a reasonable amount of time.