mirror of
https://github.com/Z3Prover/z3
synced 2026-07-18 04:55:45 +00:00
Add constant-bound contradiction shortcut for string < constraints in theory_seq (#10112)
The reported case showed expensive reasoning for lexicographic string
comparisons under the default sequence solver, and incorrect handling
expectations with `z3str3` (which does not interpret these comparisons).
This change targets the default solver path by short-circuiting
contradictory constant-bound `<` constraints earlier.
- **Theory shortcut for constant lexical bounds**
- In `theory_seq::assign_eh`, detect asserted `str.<` constraints of the
form `c < x` or `x < c` where `c` is a string constant.
- When a complementary bound on the same equivalence class is already
true, check bound consistency immediately.
- If bounds are contradictory (`!(lower < upper)`), emit a direct theory
conflict from the two active literals instead of waiting for deeper
axiom propagation.
- **Preserve existing comparison reasoning**
- Existing `check_lts` transitivity/axiom flow is retained.
- The new logic is a narrow fast path for contradictory constant bounds
and does not alter general string-order semantics.
- **Regression coverage**
- Added a solver-level regression in `src/test/seq_rewriter.cpp` for
contradictory date-like lexical bounds to ensure this class of
constraints is rejected as `unsat`.
```cpp
ctx.assert_expr(su.str.mk_lex_lt(su.str.mk_string("2024-01-01"), x));
ctx.assert_expr(su.str.mk_lex_lt(x, su.str.mk_string("2024-12-31")));
ctx.assert_expr(su.str.mk_lex_lt(x, su.str.mk_string("2023-01-01")));
ENSURE(ctx.check() == l_false);
```
---------
Co-authored-by: copilot-swe-agent[bot] <198982749+Copilot@users.noreply.github.com>
This commit is contained in:
parent
038b367d68
commit
710b4082d1
2 changed files with 91 additions and 0 deletions
|
|
@ -15,6 +15,7 @@ Tests:
|
|||
17. Solver: (str.in_re x (re.range x x)) sat when len(x)=1
|
||||
18. Solver: (str.in_re x (re.range x x)) unsat when len(x)=2
|
||||
19. Solver: inverted symbolic bounds make membership unsatisfiable
|
||||
20. Solver: contradictory constant lexical bounds are unsatisfiable
|
||||
--*/
|
||||
|
||||
#include "ast/arith_decl_plugin.h"
|
||||
|
|
@ -253,6 +254,24 @@ void tst_seq_rewriter() {
|
|||
std::cout << "symbolic range solver inverted bounds unsat: " << res << "\n";
|
||||
ENSURE(res == l_false);
|
||||
}
|
||||
|
||||
// 20. unsat: contradictory constant lexical bounds.
|
||||
// "2024-01-01" < x < "2024-12-31" and x < "2023-01-01".
|
||||
// Since "2023-01-01" < "2024-01-01", no such x exists.
|
||||
{
|
||||
smt_params sp;
|
||||
smt::context ctx(m, sp);
|
||||
app_ref x(m.mk_fresh_const("x", str_sort), m);
|
||||
expr_ref b1(su.str.mk_string("2024-01-01"), m);
|
||||
expr_ref b2(su.str.mk_string("2024-12-31"), m);
|
||||
expr_ref b3(su.str.mk_string("2023-01-01"), m);
|
||||
ctx.assert_expr(su.str.mk_lex_lt(b1, x));
|
||||
ctx.assert_expr(su.str.mk_lex_lt(x, b2));
|
||||
ctx.assert_expr(su.str.mk_lex_lt(x, b3));
|
||||
lbool res = ctx.check();
|
||||
std::cout << "constant lexical bounds unsat: " << res << "\n";
|
||||
ENSURE(res == l_false);
|
||||
}
|
||||
}
|
||||
|
||||
std::cout << "tst_seq_rewriter: all tests passed\n";
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue