Theory of Finite Fields

examples/api/cpp/finite_field.cpp

 1/******************************************************************************
 2 * This file is part of the cvc5 project.
 3 *
 4 * Copyright (c) 2009-2026 by the authors listed in the file AUTHORS
 5 * in the top-level source directory and their institutional affiliations.
 6 * All rights reserved.  See the file COPYING in the top-level source
 7 * directory for licensing information.
 8 * ****************************************************************************
 9 *
10 * An example of solving finite field problems with cvc5's cpp API.
11 */
12
13#include <cvc5/cvc5.h>
14
15#include <cassert>
16#include <iostream>
17
18using namespace std;
19using namespace cvc5;
20
21int main()
22{
23  TermManager tm;
24  Solver solver(tm);
25  solver.setOption("produce-models", "true");
26
27  Sort f5 = tm.mkFiniteFieldSort("5");
28  Term a = tm.mkConst(f5, "a");
29  Term b = tm.mkConst(f5, "b");
30  Term z = tm.mkFiniteFieldElem("0", f5);
31
32  Term inv = tm.mkTerm(Kind::EQUAL,
33                       {tm.mkTerm(Kind::FINITE_FIELD_ADD,
34                                  {tm.mkTerm(Kind::FINITE_FIELD_MULT, {a, b}),
35                                   tm.mkFiniteFieldElem("-1", f5)}),
36                        z});
37  Term aIsTwo = tm.mkTerm(
38      Kind::EQUAL,
39      {tm.mkTerm(Kind::FINITE_FIELD_ADD, {a, tm.mkFiniteFieldElem("-2", f5)}),
40       z});
41  // ab - 1 = 0
42  solver.assertFormula(inv);
43  // a = 2
44  solver.assertFormula(aIsTwo);
45
46  // should be SAT, with b = 2^(-1)
47  Result r = solver.checkSat();
48  assert(r.isSat());
49
50  cout << "a = " << solver.getValue(a) << endl;
51  cout << "b = " << solver.getValue(b) << endl;
52
53  // b = 2
54  Term bIsTwo = tm.mkTerm(
55      Kind::EQUAL,
56      {tm.mkTerm(Kind::FINITE_FIELD_ADD, {b, tm.mkFiniteFieldElem("-2", f5)}),
57       z});
58
59  // should be UNSAT, 2*2 - 1 != 0
60  solver.assertFormula(bIsTwo);
61
62  r = solver.checkSat();
63  assert(r.isUnsat());
64}