precompute_values_e(min_int, _, _, _, _, integer(MinInt)) :- !,
get_preference(minint, MinInt).
precompute_values_e(max_int, _, _, _, _, integer(MaxInt)) :- !,
get_preference(maxint, MaxInt).
precompute_values_e(forall(TIDs,LHS,RHS), pred, Info, Options, ScopeIds, Res) :-
member(instantiate_quantifier_limit(L), Options),
L \== 0,
instantiate_quantifier_possible(forall(TIDs,LHS,RHS), pred, Info, Options, ScopeIds, NOptions, TRes),
( TRes == truth
-> Res = truth % no instantiation found, universal quantification is true
; precompute_values3(TRes, NOptions, [], b(Res,pred,_)) % TODO: check this, what about ScopeIDs?
).
precompute_values_e(exists(TIDs,LHS), pred, Info, Options, ScopeIds, Res) :-
member(instantiate_quantifier_limit(L), Options),
L \== 0,
instantiate_quantifier_possible(exists(TIDs,LHS), pred, Info, Options, ScopeIds, NOptions, TRes),
( TRes == falsity
-> Res = falsity % no instantiation found, existential quantification is false
; precompute_values3(TRes, NOptions, [], b(Res,pred,_)) % TODO: check this, what about ScopeIDs?
).
precompute_values_e(comprehension_set([Id,LambdaRes],Body), _, _, Options, ScopeIds, SetExtension) :-
% e.g., %(i : 1..3|0)
LambdaRes = b(identifier('_lambda_result_'),_,_),
Body = b(conjunct(Member,LambdaEq),pred,_),
remove_all_infos(Id, CId),
remove_all_infos(LambdaRes, CLambdaRes),
Member = b(member(CId,Domain),pred,_),
LambdaEq = b(equal(CLambdaRes,RangeVal),pred,_),
compute_ground_lambda(Id, Domain, RangeVal, ScopeIds, Options, ComputedSet),
!,
construct_set_extension(ComputedSet,SetExtension).
precompute_values_e(interval(A,B), _, _, Options, ScopeIds, SetExtension) :-
rewrite_set_to_list_of_asts(b(interval(A,B),set(integer),[]), ScopeIds, Options, List),
!,
construct_set_extension(List,SetExtension).
precompute_values_e(Pow, _, _, Options, ScopeIds, Precomputed) :-
SetAst = b(set_extension(List),set(Type),[]),
( Pow = pow_subset(Arg),
PowAst = b(pow_subset(SetAst),set(set(Type)),[])
; Pow = pow1_subset(Arg),
PowAst = b(pow1_subset(SetAst),set(set(Type)),[])
),
rewrite_set_to_list_of_asts(Arg, ScopeIds, Options, List),
is_a_list_of_values(List),
length(List, Len),
( Pow = pow_subset(Arg)
-> PowCard is 2**Len
; PowCard is 2**Len - 1
),
( member(instantiate_sets_limit(SetLimit), Options)
-> PowCard =< SetLimit
; true
),
List = [b(_,Type,_)|_],
!,
b_compute_expression_nowf(PowAst, [], [], TPrecomputedVal,'SMT precomputation',0),
normalise_value_for_var(solver_result, force, TPrecomputedVal, PrecomputedVal),
Precomputed = value(PrecomputedVal).
precompute_values_e(reverse(Arg), _, _, Options, ScopeIds, SetExtension) :-
rewrite_set_to_list_of_asts(Arg, ScopeIds, Options, List),
is_a_list_of_values(List),
compute_inverse(List, InvList),
!,
construct_set_extension(InvList,SetExtension).
precompute_values_e(cartesian_product(SetA,SetB), _, _, Options, ScopeIds, SetExtension) :-
rewrite_set_to_list_of_asts(SetA, ScopeIds, Options, ListA),
rewrite_set_to_list_of_asts(SetB, ScopeIds, Options, ListB),
get_texpr_type(SetA, set(InTypeA)),
get_texpr_type(SetB, set(InTypeB)),
compute_cartesian_product(InTypeA, InTypeB, ListA, ListB, CartList),
!,
construct_set_extension(CartList,SetExtension).
precompute_values_e(BOP, _Type, _Info, Options, ScopeIds, Res) :-
binary_connective(BOP,F,A,B),
!,
binary_connective(Res,F,NA,NB),
precompute_values_non_recursive(Options, ScopeIds, A, NA),
precompute_values_non_recursive(Options, ScopeIds, B, NB). % we ignore allow_recursive_call option; all optimisations are local
precompute_values_e(Expr, Type, Info, Options, ScopeIds, Res) :-
syntaxtransformation(Expr, Subs, Names, NSubs, NExpr),
( Names \= []
-> maplist(get_texpr_id, Names, IdNames),
append(IdNames, ScopeIds, NScopeIds)
; NScopeIds = ScopeIds),
!,
maplist(precompute_values_non_recursive(Options, NScopeIds), Subs, NSubs),
( ( select(allow_recursive_call, Options, Options2),
\+ no_recursive_computation(NExpr)
)
-> precompute_values_e(NExpr, Type, Info, Options2, NScopeIds, Res) % Warning: this can cause a quadratic processing time !
; Res = NExpr
).
precompute_values_e(Expr, _, _, _, _, Res) :-
add_internal_error('Unknown AST node:', precompute_values_e(Expr, _, _, _, Res)),
Res = Expr.