2

I'm trying to represent sum of integers from an integer a to an integer b of the form

\sum_{i=a}^b i

Of courese there is a closed form solution for this version, but in general I'd like to sum over expressions parameterized by i. I've currently tried to define a function symSum and described its behavior using universal quantifiers:

from z3 import *
s = Solver()
symSum = Function('symSum', IntSort(), IntSort(), IntSort())

a = Int('a')
b = Int('b')
s.add(ForAll([a,b],If(a > b,symSum(a,b) == 0,symSum(a,b) == a + symSum(a+1,b))))
x = Int('x')
s.add(x == symSum(1,5))
print(s.check())
print(s.model())

I have not gotten this code to terminate (I have only allowed it to run for a couple minutes at max though). Is this outside the capabilities of Z3?

EDIT: Looking into this a bit more I was able to use recursive functions to define this!

from z3 import *
ctx = Context()
symSum = RecFunction('symSum', IntSort(ctx), IntSort(ctx), IntSort(ctx))
a = Int('a',ctx)
b = Int('b',ctx)
RecAddDefinition(symSum, [a,b], If(a > b, 0, a + symSum(a+1,b)))
x = Int('x',ctx)

s = Solver(ctx=ctx)
s.add(symSum(1,5) == x)
print(s.check())
print(s.model())
enigma
  • 23
  • 3
  • It's cool that the recursive definition goes through, but that's unfortunately typically not good enough. If there's a model and there are enough constants around, you can get answers. Otherwise, the solver will loop. For instance, try something like: `s.add(symSum(x, 10) == 35)`. You'll find that the solver will loop forever. – alias Mar 19 '21 at 00:29

1 Answers1

2

Yes; this is beyond the current capabilities of SMT solvers.

Imagine how you'd prove something like this by hand. You'd have to do induction on the natural numbers. SMT solvers do not perform induction, at least not out-of-the box. You can coax them to do so with a lot of helper lemmas and careful guiding via what's known as patterns; but it's not something they're designed for, or even good at. At least not for the time being.

See this answer for more details regarding a relevant question: Is it possible to prove this defined function is an involution in z3?

Having said that, recent versions of SMTLib does include capabilities for definitions recursive functions. (See https://smtlib.cs.uiowa.edu/papers/smt-lib-reference-v2.6-r2017-07-18.pdf, Section 4.2.3.) And z3 and other solvers have some support for the new syntax, though they can't really prove any interesting properties of these functions. I suspect the direction of the community is that eventually some level of (user-guided) induction will become part of the toolbox offered by these solvers, but that is currently not the case for the time being.

alias
  • 28,120
  • 2
  • 23
  • 40