3
0
Fork 0
mirror of https://github.com/Z3Prover/z3 synced 2026-03-15 17:49:59 +00:00

Add missing AST query methods to Java API (#8977)

* add Expr.isGround() to Java API

Expose Z3_is_ground as a public method on Expr. Returns true when the
expression contains no free variables.

* add Expr.isLambda() to Java API

Expose Z3_is_lambda as a public method on Expr. Returns true when the
expression is a lambda quantifier.

* add AST.getDepth() to Java API

Expose Z3_get_depth as a public method on AST. Returns the maximum
number of nodes on any path from root to leaf.

* add ArraySort.getArity() to Java API

Expose Z3_get_array_arity as a public method on ArraySort. Returns
the number of dimensions of a multi-dimensional array sort.

* add DatatypeSort.isRecursive() to Java API

Expose Z3_is_recursive_datatype_sort as a public method on
DatatypeSort. Returns true when the datatype refers to itself.

* add FPExpr.isNumeral() to Java API

Expose Z3_fpa_is_numeral as a public method on FPExpr. Returns true
when the expression is a concrete floating-point value.

* add isGroundExample test to JavaExample

Test Expr.isGround() on constants, variables, and compound
expressions.

* add astDepthExample test to JavaExample

Test AST.getDepth() on leaf nodes and nested expressions to verify
the depth computation.

* add arrayArityExample test to JavaExample

Test ArraySort.getArity() on single-domain and multi-domain array
sorts.

* add recursiveDatatypeExample test to JavaExample

Test DatatypeSort.isRecursive() on a recursive list datatype and a
non-recursive pair datatype.

* add fpNumeralExample test to JavaExample

Test FPExpr.isNumeral() on a floating point constant and a symbolic
variable.

* add isLambdaExample test to JavaExample

Test Expr.isLambda() on a lambda expression and a plain variable.
This commit is contained in:
Angelica Moreira 2026-03-14 10:13:42 -07:00 committed by GitHub
parent 6e5971641f
commit b8e15f2121
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 205 additions and 1 deletions

View file

@ -2277,6 +2277,143 @@ class JavaExample
}
@SuppressWarnings("unchecked")
void isGroundExample(Context ctx) throws TestFailedException
{
System.out.println("IsGroundExample");
Log.append("IsGroundExample");
// a constant integer is ground
IntExpr five = ctx.mkInt(5);
if (!five.isGround())
throw new TestFailedException();
// a free variable is not ground
IntExpr x = ctx.mkIntConst("x");
if (!x.isGround())
throw new TestFailedException();
// an addition of constants is ground
Expr sum = ctx.mkAdd(ctx.mkInt(1), ctx.mkInt(2));
if (!sum.isGround())
throw new TestFailedException();
System.out.println("IsGroundExample passed.");
}
@SuppressWarnings("unchecked")
void astDepthExample(Context ctx) throws TestFailedException
{
System.out.println("AstDepthExample");
Log.append("AstDepthExample");
// a plain integer constant has depth 1
IntExpr five = ctx.mkInt(5);
if (five.getDepth() != 1)
throw new TestFailedException();
// (x + 1) should have depth 2
IntExpr x = ctx.mkIntConst("x");
Expr sum = ctx.mkAdd(x, ctx.mkInt(1));
if (sum.getDepth() != 2)
throw new TestFailedException();
// nested: (x + 1) * y should have depth 3
IntExpr y = ctx.mkIntConst("y");
Expr prod = ctx.mkMul(sum, y);
if (prod.getDepth() != 3)
throw new TestFailedException();
System.out.println("AstDepthExample passed.");
}
void arrayArityExample(Context ctx) throws TestFailedException
{
System.out.println("ArrayArityExample");
Log.append("ArrayArityExample");
// Array Int -> Int has arity 1
ArraySort<IntSort, IntSort> arr1 = ctx.mkArraySort(ctx.getIntSort(), ctx.getIntSort());
if (arr1.getArity() != 1)
throw new TestFailedException();
// Array (Int, Bool) -> Int has arity 2
ArraySort arr2 = ctx.mkArraySort(new Sort[]{ctx.getIntSort(), ctx.getBoolSort()}, ctx.getIntSort());
if (arr2.getArity() != 2)
throw new TestFailedException();
System.out.println("ArrayArityExample passed.");
}
void recursiveDatatypeExample(Context ctx) throws TestFailedException
{
System.out.println("RecursiveDatatypeExample");
Log.append("RecursiveDatatypeExample");
// a list sort is recursive (cons refers back to the list)
Constructor<Sort> nil = ctx.mkConstructor("nil", "is_nil", null, null, null);
Constructor<Sort> cons = ctx.mkConstructor("cons", "is_cons",
new String[]{"head", "tail"},
new Sort[]{ctx.getIntSort(), null},
new int[]{0, 0});
DatatypeSort<Sort> intList = ctx.mkDatatypeSort("intlist", new Constructor[]{nil, cons});
if (!intList.isRecursive())
throw new TestFailedException();
// a simple pair sort is not recursive
Constructor<Sort> mkPair = ctx.mkConstructor("mkpair", "is_pair",
new String[]{"fst", "snd"},
new Sort[]{ctx.getIntSort(), ctx.getBoolSort()},
null);
DatatypeSort<Sort> pair = ctx.mkDatatypeSort("Pair", new Constructor[]{mkPair});
if (pair.isRecursive())
throw new TestFailedException();
System.out.println("RecursiveDatatypeExample passed.");
}
void fpNumeralExample(Context ctx) throws TestFailedException
{
System.out.println("FpNumeralExample");
Log.append("FpNumeralExample");
FPSort fpsort = ctx.mkFPSort32();
// a floating point numeral
FPExpr fpval = (FPExpr) ctx.mkFP(3.14, fpsort);
if (!fpval.isNumeral())
throw new TestFailedException();
// a symbolic FP variable is not a numeral
FPExpr fpvar = (FPExpr) ctx.mkConst("fpx", fpsort);
if (fpvar.isNumeral())
throw new TestFailedException();
System.out.println("FpNumeralExample passed.");
}
@SuppressWarnings("unchecked")
void isLambdaExample(Context ctx) throws TestFailedException
{
System.out.println("IsLambdaExample");
Log.append("IsLambdaExample");
// build lambda x : Int . x + 1
IntExpr x = (IntExpr) ctx.mkBound(0, ctx.getIntSort());
Expr body = ctx.mkAdd(x, ctx.mkInt(1));
Expr lam = ctx.mkLambda(new Sort[]{ctx.getIntSort()},
new Symbol[]{ctx.mkSymbol("x")}, body);
if (!lam.isLambda())
throw new TestFailedException();
// a regular expression is not a lambda
IntExpr y = ctx.mkIntConst("y");
if (y.isLambda())
throw new TestFailedException();
System.out.println("IsLambdaExample passed.");
}
public static void main(String[] args)
{
JavaExample p = new JavaExample();
@ -2328,6 +2465,12 @@ class JavaExample
p.finiteDomainExample(ctx);
p.floatingPointExample1(ctx);
// core dumps: p.floatingPointExample2(ctx);
p.isGroundExample(ctx);
p.astDepthExample(ctx);
p.arrayArityExample(ctx);
p.recursiveDatatypeExample(ctx);
p.fpNumeralExample(ctx);
p.isLambdaExample(ctx);
}
{ // These examples need proof generation turned on.