YAP 7.1.0
All Classes Files Functions Variables Typedefs Enumerations Enumerator Macros Modules Pages
exo_interval.yap
Go to the documentation of this file.
1/**
2 * @file exo_interval.yap
3 * @author VITOR SANTOS COSTA <vsc@VITORs-MBP.lan>
4 * @date 2013
5 *
6 * @brief This file implements a very simple interval solver
7 * designed to interact with the exo
8 * data-base.
9 * It assumes simple queries and a contiguous interval,
10 * and does not really expect to do non-trivial
11 * constraint propagation and solving.
12 *
13 *
14*/
15:- module(exo_interval,
16 [max/2,
17 min/2,
18 any/2,
19 max/1,
20 min/1,
21 maximum/1,
22 minimum/1,
23 any/1,
24 (#<)/2,
25 (#>)/2,
26 (#=<)/2,
27 (#>=)/2,
28 (#=)/2,
29 op(700, xfx, (#>)),
30 op(700, xfx, (#<)),
31 op(700, xfx, (#>=)),
32 op(700, xfx, (#=<)),
33 op(700, xfx, (#=))]).
34
35
36/**
37
38@defgroup exo_interval Exo Intervals
39@ingroup YAPLibrary
40@{
41
42This package assumes you use exo-compilation, that is, that you loaded
43the pedicate using the `exo` option to load_files/2, In this
44case, YAP includes a package for improved search on intervals of
45integers.
46
47The package is activated by `udi` declarations that state what is
48the argument of interest:
49
50```
51:- udi(diagnoses(exo_interval,?,?)).
52
53:- load_files(db, [consult(exo)]).
54```
55It is designed to optimise the following type of queries:
56
57```
58?- max(X, diagnoses(X, 9, Y), X).
59
60?- min(X, diagnoses(X, 9, 36211117), X).
61
62?- X #< Y, min(X, diagnoses(X, 9, 36211117), X ), diagnoses(Y, 9, _).
63```
64The first argument gives the time, the second the patient, and the
65third the condition code. The first query should find the last time
66the patient 9 had any code reported, the second looks for the first
67report of code 36211117, and the last searches for reports after this
68one. All queries run in constant or log(n) time.
69
70
71 */
72
73/** @pred max( _X_, _Vs_)
74First Argument is the greatest element of a list.
75
76+ lex_order( _Vs_)
77All elements must be ordered.
78
79
80
81The following predicates control search:
82
83
84*/
85/** @pred max(+ _Expression_)
86Maximizes _Expression_ within the current constraint store. This is
87the same as computing the supremum and equating the expression to that
88supremum.
89
90
91*/
92/** @pred min( _X_, _Vs_)
93First Argument is the least element of a list.
94
95
96*/
97/** @pred min(+ _Expression_)
98Minimizes _Expression_ within the current constraint store. This is
99the same as computing the infimum and equation the expression to that
100infimum.
101
102
103*/
104:- meta_predicate max(?,0), min(?,0), any(?,0).
105
106max(X, G) :-
107 insert_atts(X, i(_,_,max)),
108 call(G).
109
110min(X, G) :-
111 insert_atts(X, i(_,_,min)),
112 call(G).
113
114max(X) :-
115 insert_atts(X, i(_,_,max)).
116
117maximum(X) :-
118 insert_atts(X, i(_,_,maximum)).
119
120any(X) :-
121 insert_atts(X, i(_,_,any)).
122
123min(X) :-
124 insert_atts(X, i(_,_,min)).
125
126minimum(X) :-
127 insert_atts(X, i(_,_,minimum)).
128
129least(X) :-
130 insert_atts(X, i(_,_,least)).
131
132X insert_atts Y :-
133 ( var(X) -> insert_atts(X, i(Y,_,_))
134 ;
135 ( var(Y) -> insert_atts(Y, i(_,X,_) ) ;
136 insert_atts
137 )
138 ;
139 var(Y) -> insert_atts(Y, i(_,X,_))
140 ;
141 X > Y
142 ).
143
144X #>= Y :-
145 ( var(X) -> insert_atts(X, i(Y-1,_,_))
146 ;
147 X >= Y
148 ).
149
150X #< Y :-
151 ( var(X) -> insert_atts(X, i(_,Y,_))
152 ;
153 X < Y
154 ).
155
156X #=< Y :-
157 ( var(X) -> insert_atts(X, i(Y+1,_,_))
158 ;
159 X =< Y
160 ).
161
162X #= Y :-
163 ( var(X) -> insert_atts(X, i(Y-1,Y+1,_)) ;
164 X =:= Y
165 ).
166
167
168attribute_goals(X) -->
169 { get_attr(X, exo_interval, Op) },
170 ( { Op = max } -> [max(X)] ;
171 { Op = } -> [min(X)] ;
172 { Op = '>'(Y) } -> [X Y] ;
173 { Op = '<'(Y) } -> [X Y] ;
174 { Op = range(A,B,C) } ->
175 range_min(A,X),
176 range_max(B,X),
177 range_op(C, X)
178 ).
179
180range_min(Y, _X) -->
181 { var(Y) }, !,
182 [].
183range_min(Y, X) -->
184 [X #> Y].
185
186range_max(Y, _X) -->
187 { var(Y) }, !,
188 [].
189range_max(Y, X) -->
190 [X #< Y].
191
192range_op(Y, _X) -->
193 { var(Y) }, !,
194 [].
195range_op(Y, X) -->
196 { Op =.. [Y, X] },
197 [Op].
198
199insert_atts(V, Att) :-
200 ( nonvar(V) ->
201 throw( error(uninstantion_error(V), exo_interval) )
202 ; attvar(V) ->
203 get_attr(V, exo_interval, Att0),
204 expand_atts(Att, Att0, NAtt)
205 ;
206 NAtt = Att
207 ),
208 put_attr(V, exo_interval, NAtt).
209
210expand_atts(i(A1, B1, C1), i(A2, B2, C2), i(A3,B3,C3)) :-
211 expand_min(A1, A2, A3),
212 expand_max(B1, B2, B3),
213 expand_op(C1, C2, C3).
214
215expand_min(A1, A2, A3) :-
216 (var(A1) -> A3 = A2;
217 var(A2) -> A3 = A1;
218 ground(A1), ground(A2) -> A3 is max(A1,A2) ;
219 A3 = max(A1,A2)
220 ).
221
222expand_max(A1, A2, A3) :-
223 (var(A1) -> A3 = A2;
224 var(A2) -> A3 = A1;
225 ground(A1), ground(A2) -> A3 is min(A1,A2) ;
226 A3 = min(A1,A2)
227 ).
228
229expand_op(A1, A2, A3) :-
230 (var(A1) -> A3 = A2;
231 var(A2) -> A3 = A1;
232 A1 == A2 -> A3 = A1;
233 A1 == var -> A3 = var;
234 A2 == var -> A3 = var;
235 A2 == var, A1 = var -> A3 = var;
236 A1 == var, A2 = var -> A3 = var;
237 A1 == var -> A3 = var; A2 == var -> A3 = var;
238 A1 == var -> A3 = var; A2 == var -> A3 = var;
239 A3 = var
240 ).
241%% @}
242
243
throw(+ Ball)
attvar( -Var)
get_attr( + Var,+ Module,- Value)
put_attr(+ Var,+ Module,+ Value)
call( 0:P )
ground( T)
nonvar( T)
var( T)
max(+ Expression)
max( X, Vs)
min(+ Expression)
min( X, Vs)