如何将字符串类型的约束转移到 C++ 中的 z3 求解器 expr?
How to transfer constraints of string type to z3 solver expr in C++?
比如我得到了一个约束条件:“(number < 10) && (name == "hello")”;
我现在可以执行以下操作:
context c;
expr number= c.int_const(number);
expr name = c->string_val(name.c_str());
expr constrain = ***procedure***("(number < 10) && (name == \"hello\")");
如何实现这个过程()?
Use a C++ string in z3::expr?中有一个不完整且未经验证的答案,我仍然不知道如何实现它?
我非常渴望并感谢您的帮助!谢谢!
尝试:
#include <z3++.h>
using namespace z3;
using namespace std;
int main ()
{
context c;
expr number = c.int_const("number");
expr name = c.constant(c.str_symbol("name"), c.string_sort());
expr hello = c.string_val("hello");
expr constraint = number < 10 && name == hello;
solver s(c);
s.add(constraint);
cout << s.check() << "\n";
cout << s.get_model() << "\n";
return 0;
};
假设你将上面的内容放在一个名为 a.cpp
的文件中,你可以这样编译它:
$ g++ -std=c++11 a.cpp -l z3
而当 运行 时,它会产生:
sat
(define-fun number () Int
9)
(define-fun name () String
"hello")
使用更高级别 APIs
您肯定已经注意到,在 C/C++ 中对 z3 进行编程非常冗长且极易出错。除非你有其他原因使用 C/C++,否则我建议使用更高级别的 API,例如 Python 或 Haskell,这样可以简化编程z3 在很大程度上。
Python
例如,您可以像这样在 Python 中编写问题代码:
from z3 import *
number = Int('number')
name = String('name')
s = Solver()
s.add(number < 10, name == "hello")
print(s.check())
print(s.model())
生产:
sat
[number = 9, name = "hello"]
Haskell
而在 Haskell 中,它看起来像:
import Data.SBV
ex :: IO SatResult
ex = sat $ do number <- sInteger "number"
name <- sString "name"
constrain $ number .< 10 .&& name .== literal "hello"
生产:
*Main> ex
Satisfiable. Model:
number = 9 :: Integer
name = "hello" :: String
总结
长话短说,在 C/C++ 中对 z3 进行编程(尽管完全可能)是最好避免的事情,如果您可以使用更高级别的接口。如果一定要坚持C/C++,一定要研究API:https://z3prover.github.io/api/html/namespacez3.html
比如我得到了一个约束条件:“(number < 10) && (name == "hello")”; 我现在可以执行以下操作:
context c;
expr number= c.int_const(number);
expr name = c->string_val(name.c_str());
expr constrain = ***procedure***("(number < 10) && (name == \"hello\")");
如何实现这个过程()?
Use a C++ string in z3::expr?中有一个不完整且未经验证的答案,我仍然不知道如何实现它?
我非常渴望并感谢您的帮助!谢谢!
尝试:
#include <z3++.h>
using namespace z3;
using namespace std;
int main ()
{
context c;
expr number = c.int_const("number");
expr name = c.constant(c.str_symbol("name"), c.string_sort());
expr hello = c.string_val("hello");
expr constraint = number < 10 && name == hello;
solver s(c);
s.add(constraint);
cout << s.check() << "\n";
cout << s.get_model() << "\n";
return 0;
};
假设你将上面的内容放在一个名为 a.cpp
的文件中,你可以这样编译它:
$ g++ -std=c++11 a.cpp -l z3
而当 运行 时,它会产生:
sat
(define-fun number () Int
9)
(define-fun name () String
"hello")
使用更高级别 APIs
您肯定已经注意到,在 C/C++ 中对 z3 进行编程非常冗长且极易出错。除非你有其他原因使用 C/C++,否则我建议使用更高级别的 API,例如 Python 或 Haskell,这样可以简化编程z3 在很大程度上。
Python
例如,您可以像这样在 Python 中编写问题代码:
from z3 import *
number = Int('number')
name = String('name')
s = Solver()
s.add(number < 10, name == "hello")
print(s.check())
print(s.model())
生产:
sat
[number = 9, name = "hello"]
Haskell
而在 Haskell 中,它看起来像:
import Data.SBV
ex :: IO SatResult
ex = sat $ do number <- sInteger "number"
name <- sString "name"
constrain $ number .< 10 .&& name .== literal "hello"
生产:
*Main> ex
Satisfiable. Model:
number = 9 :: Integer
name = "hello" :: String
总结
长话短说,在 C/C++ 中对 z3 进行编程(尽管完全可能)是最好避免的事情,如果您可以使用更高级别的接口。如果一定要坚持C/C++,一定要研究API:https://z3prover.github.io/api/html/namespacez3.html