annotate gcc/ada/libgnat/a-cforma.adb @ 111:04ced10e8804

gcc 7
author kono
date Fri, 27 Oct 2017 22:46:09 +0900
parents
children 84e7813d76e9
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
111
kono
parents:
diff changeset
1 ------------------------------------------------------------------------------
kono
parents:
diff changeset
2 -- --
kono
parents:
diff changeset
3 -- GNAT LIBRARY COMPONENTS --
kono
parents:
diff changeset
4 -- --
kono
parents:
diff changeset
5 -- A D A . C O N T A I N E R S . F O R M A L _ O R D E R E D _ M A P S --
kono
parents:
diff changeset
6 -- --
kono
parents:
diff changeset
7 -- B o d y --
kono
parents:
diff changeset
8 -- --
kono
parents:
diff changeset
9 -- Copyright (C) 2010-2017, Free Software Foundation, Inc. --
kono
parents:
diff changeset
10 -- --
kono
parents:
diff changeset
11 -- GNAT is free software; you can redistribute it and/or modify it under --
kono
parents:
diff changeset
12 -- terms of the GNU General Public License as published by the Free Soft- --
kono
parents:
diff changeset
13 -- ware Foundation; either version 3, or (at your option) any later ver- --
kono
parents:
diff changeset
14 -- sion. GNAT is distributed in the hope that it will be useful, but WITH- --
kono
parents:
diff changeset
15 -- OUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY --
kono
parents:
diff changeset
16 -- or FITNESS FOR A PARTICULAR PURPOSE. --
kono
parents:
diff changeset
17 -- --
kono
parents:
diff changeset
18 -- As a special exception under Section 7 of GPL version 3, you are granted --
kono
parents:
diff changeset
19 -- additional permissions described in the GCC Runtime Library Exception, --
kono
parents:
diff changeset
20 -- version 3.1, as published by the Free Software Foundation. --
kono
parents:
diff changeset
21 -- --
kono
parents:
diff changeset
22 -- You should have received a copy of the GNU General Public License and --
kono
parents:
diff changeset
23 -- a copy of the GCC Runtime Library Exception along with this program; --
kono
parents:
diff changeset
24 -- see the files COPYING3 and COPYING.RUNTIME respectively. If not, see --
kono
parents:
diff changeset
25 -- <http://www.gnu.org/licenses/>. --
kono
parents:
diff changeset
26 ------------------------------------------------------------------------------
kono
parents:
diff changeset
27
kono
parents:
diff changeset
28 with Ada.Containers.Red_Black_Trees.Generic_Bounded_Operations;
kono
parents:
diff changeset
29 pragma Elaborate_All
kono
parents:
diff changeset
30 (Ada.Containers.Red_Black_Trees.Generic_Bounded_Operations);
kono
parents:
diff changeset
31
kono
parents:
diff changeset
32 with Ada.Containers.Red_Black_Trees.Generic_Bounded_Keys;
kono
parents:
diff changeset
33 pragma Elaborate_All (Ada.Containers.Red_Black_Trees.Generic_Bounded_Keys);
kono
parents:
diff changeset
34
kono
parents:
diff changeset
35 with System; use type System.Address;
kono
parents:
diff changeset
36
kono
parents:
diff changeset
37 package body Ada.Containers.Formal_Ordered_Maps with
kono
parents:
diff changeset
38 SPARK_Mode => Off
kono
parents:
diff changeset
39 is
kono
parents:
diff changeset
40
kono
parents:
diff changeset
41 -----------------------------
kono
parents:
diff changeset
42 -- Node Access Subprograms --
kono
parents:
diff changeset
43 -----------------------------
kono
parents:
diff changeset
44
kono
parents:
diff changeset
45 -- These subprograms provide a functional interface to access fields
kono
parents:
diff changeset
46 -- of a node, and a procedural interface for modifying these values.
kono
parents:
diff changeset
47
kono
parents:
diff changeset
48 function Color
kono
parents:
diff changeset
49 (Node : Node_Type) return Ada.Containers.Red_Black_Trees.Color_Type;
kono
parents:
diff changeset
50 pragma Inline (Color);
kono
parents:
diff changeset
51
kono
parents:
diff changeset
52 function Left_Son (Node : Node_Type) return Count_Type;
kono
parents:
diff changeset
53 pragma Inline (Left_Son);
kono
parents:
diff changeset
54
kono
parents:
diff changeset
55 function Parent (Node : Node_Type) return Count_Type;
kono
parents:
diff changeset
56 pragma Inline (Parent);
kono
parents:
diff changeset
57
kono
parents:
diff changeset
58 function Right_Son (Node : Node_Type) return Count_Type;
kono
parents:
diff changeset
59 pragma Inline (Right_Son);
kono
parents:
diff changeset
60
kono
parents:
diff changeset
61 procedure Set_Color
kono
parents:
diff changeset
62 (Node : in out Node_Type;
kono
parents:
diff changeset
63 Color : Ada.Containers.Red_Black_Trees.Color_Type);
kono
parents:
diff changeset
64 pragma Inline (Set_Color);
kono
parents:
diff changeset
65
kono
parents:
diff changeset
66 procedure Set_Left (Node : in out Node_Type; Left : Count_Type);
kono
parents:
diff changeset
67 pragma Inline (Set_Left);
kono
parents:
diff changeset
68
kono
parents:
diff changeset
69 procedure Set_Right (Node : in out Node_Type; Right : Count_Type);
kono
parents:
diff changeset
70 pragma Inline (Set_Right);
kono
parents:
diff changeset
71
kono
parents:
diff changeset
72 procedure Set_Parent (Node : in out Node_Type; Parent : Count_Type);
kono
parents:
diff changeset
73 pragma Inline (Set_Parent);
kono
parents:
diff changeset
74
kono
parents:
diff changeset
75 -----------------------
kono
parents:
diff changeset
76 -- Local Subprograms --
kono
parents:
diff changeset
77 -----------------------
kono
parents:
diff changeset
78
kono
parents:
diff changeset
79 -- All need comments ???
kono
parents:
diff changeset
80
kono
parents:
diff changeset
81 generic
kono
parents:
diff changeset
82 with procedure Set_Element (Node : in out Node_Type);
kono
parents:
diff changeset
83 procedure Generic_Allocate
kono
parents:
diff changeset
84 (Tree : in out Tree_Types.Tree_Type'Class;
kono
parents:
diff changeset
85 Node : out Count_Type);
kono
parents:
diff changeset
86
kono
parents:
diff changeset
87 procedure Free (Tree : in out Map; X : Count_Type);
kono
parents:
diff changeset
88
kono
parents:
diff changeset
89 function Is_Greater_Key_Node
kono
parents:
diff changeset
90 (Left : Key_Type;
kono
parents:
diff changeset
91 Right : Node_Type) return Boolean;
kono
parents:
diff changeset
92 pragma Inline (Is_Greater_Key_Node);
kono
parents:
diff changeset
93
kono
parents:
diff changeset
94 function Is_Less_Key_Node
kono
parents:
diff changeset
95 (Left : Key_Type;
kono
parents:
diff changeset
96 Right : Node_Type) return Boolean;
kono
parents:
diff changeset
97 pragma Inline (Is_Less_Key_Node);
kono
parents:
diff changeset
98
kono
parents:
diff changeset
99 --------------------------
kono
parents:
diff changeset
100 -- Local Instantiations --
kono
parents:
diff changeset
101 --------------------------
kono
parents:
diff changeset
102
kono
parents:
diff changeset
103 package Tree_Operations is
kono
parents:
diff changeset
104 new Red_Black_Trees.Generic_Bounded_Operations
kono
parents:
diff changeset
105 (Tree_Types => Tree_Types,
kono
parents:
diff changeset
106 Left => Left_Son,
kono
parents:
diff changeset
107 Right => Right_Son);
kono
parents:
diff changeset
108
kono
parents:
diff changeset
109 use Tree_Operations;
kono
parents:
diff changeset
110
kono
parents:
diff changeset
111 package Key_Ops is
kono
parents:
diff changeset
112 new Red_Black_Trees.Generic_Bounded_Keys
kono
parents:
diff changeset
113 (Tree_Operations => Tree_Operations,
kono
parents:
diff changeset
114 Key_Type => Key_Type,
kono
parents:
diff changeset
115 Is_Less_Key_Node => Is_Less_Key_Node,
kono
parents:
diff changeset
116 Is_Greater_Key_Node => Is_Greater_Key_Node);
kono
parents:
diff changeset
117
kono
parents:
diff changeset
118 ---------
kono
parents:
diff changeset
119 -- "=" --
kono
parents:
diff changeset
120 ---------
kono
parents:
diff changeset
121
kono
parents:
diff changeset
122 function "=" (Left, Right : Map) return Boolean is
kono
parents:
diff changeset
123 Lst : Count_Type;
kono
parents:
diff changeset
124 Node : Count_Type;
kono
parents:
diff changeset
125 ENode : Count_Type;
kono
parents:
diff changeset
126
kono
parents:
diff changeset
127 begin
kono
parents:
diff changeset
128 if Length (Left) /= Length (Right) then
kono
parents:
diff changeset
129 return False;
kono
parents:
diff changeset
130 end if;
kono
parents:
diff changeset
131
kono
parents:
diff changeset
132 if Is_Empty (Left) then
kono
parents:
diff changeset
133 return True;
kono
parents:
diff changeset
134 end if;
kono
parents:
diff changeset
135
kono
parents:
diff changeset
136 Lst := Next (Left, Last (Left).Node);
kono
parents:
diff changeset
137
kono
parents:
diff changeset
138 Node := First (Left).Node;
kono
parents:
diff changeset
139 while Node /= Lst loop
kono
parents:
diff changeset
140 ENode := Find (Right, Left.Nodes (Node).Key).Node;
kono
parents:
diff changeset
141
kono
parents:
diff changeset
142 if ENode = 0 or else
kono
parents:
diff changeset
143 Left.Nodes (Node).Element /= Right.Nodes (ENode).Element
kono
parents:
diff changeset
144 then
kono
parents:
diff changeset
145 return False;
kono
parents:
diff changeset
146 end if;
kono
parents:
diff changeset
147
kono
parents:
diff changeset
148 Node := Next (Left, Node);
kono
parents:
diff changeset
149 end loop;
kono
parents:
diff changeset
150
kono
parents:
diff changeset
151 return True;
kono
parents:
diff changeset
152 end "=";
kono
parents:
diff changeset
153
kono
parents:
diff changeset
154 ------------
kono
parents:
diff changeset
155 -- Assign --
kono
parents:
diff changeset
156 ------------
kono
parents:
diff changeset
157
kono
parents:
diff changeset
158 procedure Assign (Target : in out Map; Source : Map) is
kono
parents:
diff changeset
159 procedure Append_Element (Source_Node : Count_Type);
kono
parents:
diff changeset
160
kono
parents:
diff changeset
161 procedure Append_Elements is
kono
parents:
diff changeset
162 new Tree_Operations.Generic_Iteration (Append_Element);
kono
parents:
diff changeset
163
kono
parents:
diff changeset
164 --------------------
kono
parents:
diff changeset
165 -- Append_Element --
kono
parents:
diff changeset
166 --------------------
kono
parents:
diff changeset
167
kono
parents:
diff changeset
168 procedure Append_Element (Source_Node : Count_Type) is
kono
parents:
diff changeset
169 SN : Node_Type renames Source.Nodes (Source_Node);
kono
parents:
diff changeset
170
kono
parents:
diff changeset
171 procedure Set_Element (Node : in out Node_Type);
kono
parents:
diff changeset
172 pragma Inline (Set_Element);
kono
parents:
diff changeset
173
kono
parents:
diff changeset
174 function New_Node return Count_Type;
kono
parents:
diff changeset
175 pragma Inline (New_Node);
kono
parents:
diff changeset
176
kono
parents:
diff changeset
177 procedure Insert_Post is new Key_Ops.Generic_Insert_Post (New_Node);
kono
parents:
diff changeset
178
kono
parents:
diff changeset
179 procedure Unconditional_Insert_Sans_Hint is
kono
parents:
diff changeset
180 new Key_Ops.Generic_Unconditional_Insert (Insert_Post);
kono
parents:
diff changeset
181
kono
parents:
diff changeset
182 procedure Unconditional_Insert_Avec_Hint is
kono
parents:
diff changeset
183 new Key_Ops.Generic_Unconditional_Insert_With_Hint
kono
parents:
diff changeset
184 (Insert_Post,
kono
parents:
diff changeset
185 Unconditional_Insert_Sans_Hint);
kono
parents:
diff changeset
186
kono
parents:
diff changeset
187 procedure Allocate is new Generic_Allocate (Set_Element);
kono
parents:
diff changeset
188
kono
parents:
diff changeset
189 --------------
kono
parents:
diff changeset
190 -- New_Node --
kono
parents:
diff changeset
191 --------------
kono
parents:
diff changeset
192
kono
parents:
diff changeset
193 function New_Node return Count_Type is
kono
parents:
diff changeset
194 Result : Count_Type;
kono
parents:
diff changeset
195 begin
kono
parents:
diff changeset
196 Allocate (Target, Result);
kono
parents:
diff changeset
197 return Result;
kono
parents:
diff changeset
198 end New_Node;
kono
parents:
diff changeset
199
kono
parents:
diff changeset
200 -----------------
kono
parents:
diff changeset
201 -- Set_Element --
kono
parents:
diff changeset
202 -----------------
kono
parents:
diff changeset
203
kono
parents:
diff changeset
204 procedure Set_Element (Node : in out Node_Type) is
kono
parents:
diff changeset
205 begin
kono
parents:
diff changeset
206 Node.Key := SN.Key;
kono
parents:
diff changeset
207 Node.Element := SN.Element;
kono
parents:
diff changeset
208 end Set_Element;
kono
parents:
diff changeset
209
kono
parents:
diff changeset
210 Target_Node : Count_Type;
kono
parents:
diff changeset
211
kono
parents:
diff changeset
212 -- Start of processing for Append_Element
kono
parents:
diff changeset
213
kono
parents:
diff changeset
214 begin
kono
parents:
diff changeset
215 Unconditional_Insert_Avec_Hint
kono
parents:
diff changeset
216 (Tree => Target,
kono
parents:
diff changeset
217 Hint => 0,
kono
parents:
diff changeset
218 Key => SN.Key,
kono
parents:
diff changeset
219 Node => Target_Node);
kono
parents:
diff changeset
220 end Append_Element;
kono
parents:
diff changeset
221
kono
parents:
diff changeset
222 -- Start of processing for Assign
kono
parents:
diff changeset
223
kono
parents:
diff changeset
224 begin
kono
parents:
diff changeset
225 if Target'Address = Source'Address then
kono
parents:
diff changeset
226 return;
kono
parents:
diff changeset
227 end if;
kono
parents:
diff changeset
228
kono
parents:
diff changeset
229 if Target.Capacity < Length (Source) then
kono
parents:
diff changeset
230 raise Storage_Error with "not enough capacity"; -- SE or CE? ???
kono
parents:
diff changeset
231 end if;
kono
parents:
diff changeset
232
kono
parents:
diff changeset
233 Tree_Operations.Clear_Tree (Target);
kono
parents:
diff changeset
234 Append_Elements (Source);
kono
parents:
diff changeset
235 end Assign;
kono
parents:
diff changeset
236
kono
parents:
diff changeset
237 -------------
kono
parents:
diff changeset
238 -- Ceiling --
kono
parents:
diff changeset
239 -------------
kono
parents:
diff changeset
240
kono
parents:
diff changeset
241 function Ceiling (Container : Map; Key : Key_Type) return Cursor is
kono
parents:
diff changeset
242 Node : constant Count_Type := Key_Ops.Ceiling (Container, Key);
kono
parents:
diff changeset
243
kono
parents:
diff changeset
244 begin
kono
parents:
diff changeset
245 if Node = 0 then
kono
parents:
diff changeset
246 return No_Element;
kono
parents:
diff changeset
247 end if;
kono
parents:
diff changeset
248
kono
parents:
diff changeset
249 return (Node => Node);
kono
parents:
diff changeset
250 end Ceiling;
kono
parents:
diff changeset
251
kono
parents:
diff changeset
252 -----------
kono
parents:
diff changeset
253 -- Clear --
kono
parents:
diff changeset
254 -----------
kono
parents:
diff changeset
255
kono
parents:
diff changeset
256 procedure Clear (Container : in out Map) is
kono
parents:
diff changeset
257 begin
kono
parents:
diff changeset
258 Tree_Operations.Clear_Tree (Container);
kono
parents:
diff changeset
259 end Clear;
kono
parents:
diff changeset
260
kono
parents:
diff changeset
261 -----------
kono
parents:
diff changeset
262 -- Color --
kono
parents:
diff changeset
263 -----------
kono
parents:
diff changeset
264
kono
parents:
diff changeset
265 function Color (Node : Node_Type) return Color_Type is
kono
parents:
diff changeset
266 begin
kono
parents:
diff changeset
267 return Node.Color;
kono
parents:
diff changeset
268 end Color;
kono
parents:
diff changeset
269
kono
parents:
diff changeset
270 --------------
kono
parents:
diff changeset
271 -- Contains --
kono
parents:
diff changeset
272 --------------
kono
parents:
diff changeset
273
kono
parents:
diff changeset
274 function Contains (Container : Map; Key : Key_Type) return Boolean is
kono
parents:
diff changeset
275 begin
kono
parents:
diff changeset
276 return Find (Container, Key) /= No_Element;
kono
parents:
diff changeset
277 end Contains;
kono
parents:
diff changeset
278
kono
parents:
diff changeset
279 ----------
kono
parents:
diff changeset
280 -- Copy --
kono
parents:
diff changeset
281 ----------
kono
parents:
diff changeset
282
kono
parents:
diff changeset
283 function Copy (Source : Map; Capacity : Count_Type := 0) return Map is
kono
parents:
diff changeset
284 Node : Count_Type := 1;
kono
parents:
diff changeset
285 N : Count_Type;
kono
parents:
diff changeset
286
kono
parents:
diff changeset
287 begin
kono
parents:
diff changeset
288 if 0 < Capacity and then Capacity < Source.Capacity then
kono
parents:
diff changeset
289 raise Capacity_Error;
kono
parents:
diff changeset
290 end if;
kono
parents:
diff changeset
291
kono
parents:
diff changeset
292 return Target : Map (Count_Type'Max (Source.Capacity, Capacity)) do
kono
parents:
diff changeset
293 if Length (Source) > 0 then
kono
parents:
diff changeset
294 Target.Length := Source.Length;
kono
parents:
diff changeset
295 Target.Root := Source.Root;
kono
parents:
diff changeset
296 Target.First := Source.First;
kono
parents:
diff changeset
297 Target.Last := Source.Last;
kono
parents:
diff changeset
298 Target.Free := Source.Free;
kono
parents:
diff changeset
299
kono
parents:
diff changeset
300 while Node <= Source.Capacity loop
kono
parents:
diff changeset
301 Target.Nodes (Node).Element :=
kono
parents:
diff changeset
302 Source.Nodes (Node).Element;
kono
parents:
diff changeset
303 Target.Nodes (Node).Key :=
kono
parents:
diff changeset
304 Source.Nodes (Node).Key;
kono
parents:
diff changeset
305 Target.Nodes (Node).Parent :=
kono
parents:
diff changeset
306 Source.Nodes (Node).Parent;
kono
parents:
diff changeset
307 Target.Nodes (Node).Left :=
kono
parents:
diff changeset
308 Source.Nodes (Node).Left;
kono
parents:
diff changeset
309 Target.Nodes (Node).Right :=
kono
parents:
diff changeset
310 Source.Nodes (Node).Right;
kono
parents:
diff changeset
311 Target.Nodes (Node).Color :=
kono
parents:
diff changeset
312 Source.Nodes (Node).Color;
kono
parents:
diff changeset
313 Target.Nodes (Node).Has_Element :=
kono
parents:
diff changeset
314 Source.Nodes (Node).Has_Element;
kono
parents:
diff changeset
315 Node := Node + 1;
kono
parents:
diff changeset
316 end loop;
kono
parents:
diff changeset
317
kono
parents:
diff changeset
318 while Node <= Target.Capacity loop
kono
parents:
diff changeset
319 N := Node;
kono
parents:
diff changeset
320 Formal_Ordered_Maps.Free (Tree => Target, X => N);
kono
parents:
diff changeset
321 Node := Node + 1;
kono
parents:
diff changeset
322 end loop;
kono
parents:
diff changeset
323 end if;
kono
parents:
diff changeset
324 end return;
kono
parents:
diff changeset
325 end Copy;
kono
parents:
diff changeset
326
kono
parents:
diff changeset
327 ------------
kono
parents:
diff changeset
328 -- Delete --
kono
parents:
diff changeset
329 ------------
kono
parents:
diff changeset
330
kono
parents:
diff changeset
331 procedure Delete (Container : in out Map; Position : in out Cursor) is
kono
parents:
diff changeset
332 begin
kono
parents:
diff changeset
333 if not Has_Element (Container, Position) then
kono
parents:
diff changeset
334 raise Constraint_Error with
kono
parents:
diff changeset
335 "Position cursor of Delete has no element";
kono
parents:
diff changeset
336 end if;
kono
parents:
diff changeset
337
kono
parents:
diff changeset
338 pragma Assert (Vet (Container, Position.Node),
kono
parents:
diff changeset
339 "Position cursor of Delete is bad");
kono
parents:
diff changeset
340
kono
parents:
diff changeset
341 Tree_Operations.Delete_Node_Sans_Free (Container,
kono
parents:
diff changeset
342 Position.Node);
kono
parents:
diff changeset
343 Formal_Ordered_Maps.Free (Container, Position.Node);
kono
parents:
diff changeset
344 Position := No_Element;
kono
parents:
diff changeset
345 end Delete;
kono
parents:
diff changeset
346
kono
parents:
diff changeset
347 procedure Delete (Container : in out Map; Key : Key_Type) is
kono
parents:
diff changeset
348 X : constant Node_Access := Key_Ops.Find (Container, Key);
kono
parents:
diff changeset
349
kono
parents:
diff changeset
350 begin
kono
parents:
diff changeset
351 if X = 0 then
kono
parents:
diff changeset
352 raise Constraint_Error with "key not in map";
kono
parents:
diff changeset
353 end if;
kono
parents:
diff changeset
354
kono
parents:
diff changeset
355 Tree_Operations.Delete_Node_Sans_Free (Container, X);
kono
parents:
diff changeset
356 Formal_Ordered_Maps.Free (Container, X);
kono
parents:
diff changeset
357 end Delete;
kono
parents:
diff changeset
358
kono
parents:
diff changeset
359 ------------------
kono
parents:
diff changeset
360 -- Delete_First --
kono
parents:
diff changeset
361 ------------------
kono
parents:
diff changeset
362
kono
parents:
diff changeset
363 procedure Delete_First (Container : in out Map) is
kono
parents:
diff changeset
364 X : constant Node_Access := First (Container).Node;
kono
parents:
diff changeset
365 begin
kono
parents:
diff changeset
366 if X /= 0 then
kono
parents:
diff changeset
367 Tree_Operations.Delete_Node_Sans_Free (Container, X);
kono
parents:
diff changeset
368 Formal_Ordered_Maps.Free (Container, X);
kono
parents:
diff changeset
369 end if;
kono
parents:
diff changeset
370 end Delete_First;
kono
parents:
diff changeset
371
kono
parents:
diff changeset
372 -----------------
kono
parents:
diff changeset
373 -- Delete_Last --
kono
parents:
diff changeset
374 -----------------
kono
parents:
diff changeset
375
kono
parents:
diff changeset
376 procedure Delete_Last (Container : in out Map) is
kono
parents:
diff changeset
377 X : constant Node_Access := Last (Container).Node;
kono
parents:
diff changeset
378 begin
kono
parents:
diff changeset
379 if X /= 0 then
kono
parents:
diff changeset
380 Tree_Operations.Delete_Node_Sans_Free (Container, X);
kono
parents:
diff changeset
381 Formal_Ordered_Maps.Free (Container, X);
kono
parents:
diff changeset
382 end if;
kono
parents:
diff changeset
383 end Delete_Last;
kono
parents:
diff changeset
384
kono
parents:
diff changeset
385 -------------
kono
parents:
diff changeset
386 -- Element --
kono
parents:
diff changeset
387 -------------
kono
parents:
diff changeset
388
kono
parents:
diff changeset
389 function Element (Container : Map; Position : Cursor) return Element_Type is
kono
parents:
diff changeset
390 begin
kono
parents:
diff changeset
391 if not Has_Element (Container, Position) then
kono
parents:
diff changeset
392 raise Constraint_Error with
kono
parents:
diff changeset
393 "Position cursor of function Element has no element";
kono
parents:
diff changeset
394 end if;
kono
parents:
diff changeset
395
kono
parents:
diff changeset
396 pragma Assert (Vet (Container, Position.Node),
kono
parents:
diff changeset
397 "Position cursor of function Element is bad");
kono
parents:
diff changeset
398
kono
parents:
diff changeset
399 return Container.Nodes (Position.Node).Element;
kono
parents:
diff changeset
400
kono
parents:
diff changeset
401 end Element;
kono
parents:
diff changeset
402
kono
parents:
diff changeset
403 function Element (Container : Map; Key : Key_Type) return Element_Type is
kono
parents:
diff changeset
404 Node : constant Node_Access := Find (Container, Key).Node;
kono
parents:
diff changeset
405
kono
parents:
diff changeset
406 begin
kono
parents:
diff changeset
407 if Node = 0 then
kono
parents:
diff changeset
408 raise Constraint_Error with "key not in map";
kono
parents:
diff changeset
409 end if;
kono
parents:
diff changeset
410
kono
parents:
diff changeset
411 return Container.Nodes (Node).Element;
kono
parents:
diff changeset
412 end Element;
kono
parents:
diff changeset
413
kono
parents:
diff changeset
414 ---------------------
kono
parents:
diff changeset
415 -- Equivalent_Keys --
kono
parents:
diff changeset
416 ---------------------
kono
parents:
diff changeset
417
kono
parents:
diff changeset
418 function Equivalent_Keys (Left, Right : Key_Type) return Boolean is
kono
parents:
diff changeset
419 begin
kono
parents:
diff changeset
420 if Left < Right
kono
parents:
diff changeset
421 or else Right < Left
kono
parents:
diff changeset
422 then
kono
parents:
diff changeset
423 return False;
kono
parents:
diff changeset
424 else
kono
parents:
diff changeset
425 return True;
kono
parents:
diff changeset
426 end if;
kono
parents:
diff changeset
427 end Equivalent_Keys;
kono
parents:
diff changeset
428
kono
parents:
diff changeset
429 -------------
kono
parents:
diff changeset
430 -- Exclude --
kono
parents:
diff changeset
431 -------------
kono
parents:
diff changeset
432
kono
parents:
diff changeset
433 procedure Exclude (Container : in out Map; Key : Key_Type) is
kono
parents:
diff changeset
434 X : constant Node_Access := Key_Ops.Find (Container, Key);
kono
parents:
diff changeset
435 begin
kono
parents:
diff changeset
436 if X /= 0 then
kono
parents:
diff changeset
437 Tree_Operations.Delete_Node_Sans_Free (Container, X);
kono
parents:
diff changeset
438 Formal_Ordered_Maps.Free (Container, X);
kono
parents:
diff changeset
439 end if;
kono
parents:
diff changeset
440 end Exclude;
kono
parents:
diff changeset
441
kono
parents:
diff changeset
442 ----------
kono
parents:
diff changeset
443 -- Find --
kono
parents:
diff changeset
444 ----------
kono
parents:
diff changeset
445
kono
parents:
diff changeset
446 function Find (Container : Map; Key : Key_Type) return Cursor is
kono
parents:
diff changeset
447 Node : constant Count_Type := Key_Ops.Find (Container, Key);
kono
parents:
diff changeset
448
kono
parents:
diff changeset
449 begin
kono
parents:
diff changeset
450 if Node = 0 then
kono
parents:
diff changeset
451 return No_Element;
kono
parents:
diff changeset
452 end if;
kono
parents:
diff changeset
453
kono
parents:
diff changeset
454 return (Node => Node);
kono
parents:
diff changeset
455 end Find;
kono
parents:
diff changeset
456
kono
parents:
diff changeset
457 -----------
kono
parents:
diff changeset
458 -- First --
kono
parents:
diff changeset
459 -----------
kono
parents:
diff changeset
460
kono
parents:
diff changeset
461 function First (Container : Map) return Cursor is
kono
parents:
diff changeset
462 begin
kono
parents:
diff changeset
463 if Length (Container) = 0 then
kono
parents:
diff changeset
464 return No_Element;
kono
parents:
diff changeset
465 end if;
kono
parents:
diff changeset
466
kono
parents:
diff changeset
467 return (Node => Container.First);
kono
parents:
diff changeset
468 end First;
kono
parents:
diff changeset
469
kono
parents:
diff changeset
470 -------------------
kono
parents:
diff changeset
471 -- First_Element --
kono
parents:
diff changeset
472 -------------------
kono
parents:
diff changeset
473
kono
parents:
diff changeset
474 function First_Element (Container : Map) return Element_Type is
kono
parents:
diff changeset
475 begin
kono
parents:
diff changeset
476 if Is_Empty (Container) then
kono
parents:
diff changeset
477 raise Constraint_Error with "map is empty";
kono
parents:
diff changeset
478 end if;
kono
parents:
diff changeset
479
kono
parents:
diff changeset
480 return Container.Nodes (First (Container).Node).Element;
kono
parents:
diff changeset
481 end First_Element;
kono
parents:
diff changeset
482
kono
parents:
diff changeset
483 ---------------
kono
parents:
diff changeset
484 -- First_Key --
kono
parents:
diff changeset
485 ---------------
kono
parents:
diff changeset
486
kono
parents:
diff changeset
487 function First_Key (Container : Map) return Key_Type is
kono
parents:
diff changeset
488 begin
kono
parents:
diff changeset
489 if Is_Empty (Container) then
kono
parents:
diff changeset
490 raise Constraint_Error with "map is empty";
kono
parents:
diff changeset
491 end if;
kono
parents:
diff changeset
492
kono
parents:
diff changeset
493 return Container.Nodes (First (Container).Node).Key;
kono
parents:
diff changeset
494 end First_Key;
kono
parents:
diff changeset
495
kono
parents:
diff changeset
496 -----------
kono
parents:
diff changeset
497 -- Floor --
kono
parents:
diff changeset
498 -----------
kono
parents:
diff changeset
499
kono
parents:
diff changeset
500 function Floor (Container : Map; Key : Key_Type) return Cursor is
kono
parents:
diff changeset
501 Node : constant Count_Type := Key_Ops.Floor (Container, Key);
kono
parents:
diff changeset
502
kono
parents:
diff changeset
503 begin
kono
parents:
diff changeset
504 if Node = 0 then
kono
parents:
diff changeset
505 return No_Element;
kono
parents:
diff changeset
506 end if;
kono
parents:
diff changeset
507
kono
parents:
diff changeset
508 return (Node => Node);
kono
parents:
diff changeset
509 end Floor;
kono
parents:
diff changeset
510
kono
parents:
diff changeset
511 ------------------
kono
parents:
diff changeset
512 -- Formal_Model --
kono
parents:
diff changeset
513 ------------------
kono
parents:
diff changeset
514
kono
parents:
diff changeset
515 package body Formal_Model is
kono
parents:
diff changeset
516
kono
parents:
diff changeset
517 ----------
kono
parents:
diff changeset
518 -- Find --
kono
parents:
diff changeset
519 ----------
kono
parents:
diff changeset
520
kono
parents:
diff changeset
521 function Find
kono
parents:
diff changeset
522 (Container : K.Sequence;
kono
parents:
diff changeset
523 Key : Key_Type) return Count_Type
kono
parents:
diff changeset
524 is
kono
parents:
diff changeset
525 begin
kono
parents:
diff changeset
526 for I in 1 .. K.Length (Container) loop
kono
parents:
diff changeset
527 if Equivalent_Keys (Key, K.Get (Container, I)) then
kono
parents:
diff changeset
528 return I;
kono
parents:
diff changeset
529 elsif Key < K.Get (Container, I) then
kono
parents:
diff changeset
530 return 0;
kono
parents:
diff changeset
531 end if;
kono
parents:
diff changeset
532 end loop;
kono
parents:
diff changeset
533 return 0;
kono
parents:
diff changeset
534 end Find;
kono
parents:
diff changeset
535
kono
parents:
diff changeset
536 -------------------------
kono
parents:
diff changeset
537 -- K_Bigger_Than_Range --
kono
parents:
diff changeset
538 -------------------------
kono
parents:
diff changeset
539
kono
parents:
diff changeset
540 function K_Bigger_Than_Range
kono
parents:
diff changeset
541 (Container : K.Sequence;
kono
parents:
diff changeset
542 Fst : Positive_Count_Type;
kono
parents:
diff changeset
543 Lst : Count_Type;
kono
parents:
diff changeset
544 Key : Key_Type) return Boolean
kono
parents:
diff changeset
545 is
kono
parents:
diff changeset
546 begin
kono
parents:
diff changeset
547 for I in Fst .. Lst loop
kono
parents:
diff changeset
548 if not (K.Get (Container, I) < Key) then
kono
parents:
diff changeset
549 return False;
kono
parents:
diff changeset
550 end if;
kono
parents:
diff changeset
551 end loop;
kono
parents:
diff changeset
552 return True;
kono
parents:
diff changeset
553 end K_Bigger_Than_Range;
kono
parents:
diff changeset
554
kono
parents:
diff changeset
555 ---------------
kono
parents:
diff changeset
556 -- K_Is_Find --
kono
parents:
diff changeset
557 ---------------
kono
parents:
diff changeset
558
kono
parents:
diff changeset
559 function K_Is_Find
kono
parents:
diff changeset
560 (Container : K.Sequence;
kono
parents:
diff changeset
561 Key : Key_Type;
kono
parents:
diff changeset
562 Position : Count_Type) return Boolean
kono
parents:
diff changeset
563 is
kono
parents:
diff changeset
564 begin
kono
parents:
diff changeset
565 for I in 1 .. Position - 1 loop
kono
parents:
diff changeset
566 if Key < K.Get (Container, I) then
kono
parents:
diff changeset
567 return False;
kono
parents:
diff changeset
568 end if;
kono
parents:
diff changeset
569 end loop;
kono
parents:
diff changeset
570
kono
parents:
diff changeset
571 if Position < K.Length (Container) then
kono
parents:
diff changeset
572 for I in Position + 1 .. K.Length (Container) loop
kono
parents:
diff changeset
573 if K.Get (Container, I) < Key then
kono
parents:
diff changeset
574 return False;
kono
parents:
diff changeset
575 end if;
kono
parents:
diff changeset
576 end loop;
kono
parents:
diff changeset
577 end if;
kono
parents:
diff changeset
578 return True;
kono
parents:
diff changeset
579 end K_Is_Find;
kono
parents:
diff changeset
580
kono
parents:
diff changeset
581 --------------------------
kono
parents:
diff changeset
582 -- K_Smaller_Than_Range --
kono
parents:
diff changeset
583 --------------------------
kono
parents:
diff changeset
584
kono
parents:
diff changeset
585 function K_Smaller_Than_Range
kono
parents:
diff changeset
586 (Container : K.Sequence;
kono
parents:
diff changeset
587 Fst : Positive_Count_Type;
kono
parents:
diff changeset
588 Lst : Count_Type;
kono
parents:
diff changeset
589 Key : Key_Type) return Boolean
kono
parents:
diff changeset
590 is
kono
parents:
diff changeset
591 begin
kono
parents:
diff changeset
592 for I in Fst .. Lst loop
kono
parents:
diff changeset
593 if not (Key < K.Get (Container, I)) then
kono
parents:
diff changeset
594 return False;
kono
parents:
diff changeset
595 end if;
kono
parents:
diff changeset
596 end loop;
kono
parents:
diff changeset
597 return True;
kono
parents:
diff changeset
598 end K_Smaller_Than_Range;
kono
parents:
diff changeset
599
kono
parents:
diff changeset
600 ----------
kono
parents:
diff changeset
601 -- Keys --
kono
parents:
diff changeset
602 ----------
kono
parents:
diff changeset
603
kono
parents:
diff changeset
604 function Keys (Container : Map) return K.Sequence is
kono
parents:
diff changeset
605 Position : Count_Type := Container.First;
kono
parents:
diff changeset
606 R : K.Sequence;
kono
parents:
diff changeset
607
kono
parents:
diff changeset
608 begin
kono
parents:
diff changeset
609 -- Can't use First, Next or Element here, since they depend on models
kono
parents:
diff changeset
610 -- for their postconditions.
kono
parents:
diff changeset
611
kono
parents:
diff changeset
612 while Position /= 0 loop
kono
parents:
diff changeset
613 R := K.Add (R, Container.Nodes (Position).Key);
kono
parents:
diff changeset
614 Position := Tree_Operations.Next (Container, Position);
kono
parents:
diff changeset
615 end loop;
kono
parents:
diff changeset
616
kono
parents:
diff changeset
617 return R;
kono
parents:
diff changeset
618 end Keys;
kono
parents:
diff changeset
619
kono
parents:
diff changeset
620 ----------------------------
kono
parents:
diff changeset
621 -- Lift_Abstraction_Level --
kono
parents:
diff changeset
622 ----------------------------
kono
parents:
diff changeset
623
kono
parents:
diff changeset
624 procedure Lift_Abstraction_Level (Container : Map) is null;
kono
parents:
diff changeset
625
kono
parents:
diff changeset
626 -----------
kono
parents:
diff changeset
627 -- Model --
kono
parents:
diff changeset
628 -----------
kono
parents:
diff changeset
629
kono
parents:
diff changeset
630 function Model (Container : Map) return M.Map is
kono
parents:
diff changeset
631 Position : Count_Type := Container.First;
kono
parents:
diff changeset
632 R : M.Map;
kono
parents:
diff changeset
633
kono
parents:
diff changeset
634 begin
kono
parents:
diff changeset
635 -- Can't use First, Next or Element here, since they depend on models
kono
parents:
diff changeset
636 -- for their postconditions.
kono
parents:
diff changeset
637
kono
parents:
diff changeset
638 while Position /= 0 loop
kono
parents:
diff changeset
639 R :=
kono
parents:
diff changeset
640 M.Add
kono
parents:
diff changeset
641 (Container => R,
kono
parents:
diff changeset
642 New_Key => Container.Nodes (Position).Key,
kono
parents:
diff changeset
643 New_Item => Container.Nodes (Position).Element);
kono
parents:
diff changeset
644
kono
parents:
diff changeset
645 Position := Tree_Operations.Next (Container, Position);
kono
parents:
diff changeset
646 end loop;
kono
parents:
diff changeset
647
kono
parents:
diff changeset
648 return R;
kono
parents:
diff changeset
649 end Model;
kono
parents:
diff changeset
650
kono
parents:
diff changeset
651 -------------------------
kono
parents:
diff changeset
652 -- P_Positions_Shifted --
kono
parents:
diff changeset
653 -------------------------
kono
parents:
diff changeset
654
kono
parents:
diff changeset
655 function P_Positions_Shifted
kono
parents:
diff changeset
656 (Small : P.Map;
kono
parents:
diff changeset
657 Big : P.Map;
kono
parents:
diff changeset
658 Cut : Positive_Count_Type;
kono
parents:
diff changeset
659 Count : Count_Type := 1) return Boolean
kono
parents:
diff changeset
660 is
kono
parents:
diff changeset
661 begin
kono
parents:
diff changeset
662 for Cu of Small loop
kono
parents:
diff changeset
663 if not P.Has_Key (Big, Cu) then
kono
parents:
diff changeset
664 return False;
kono
parents:
diff changeset
665 end if;
kono
parents:
diff changeset
666 end loop;
kono
parents:
diff changeset
667
kono
parents:
diff changeset
668 for Cu of Big loop
kono
parents:
diff changeset
669 declare
kono
parents:
diff changeset
670 Pos : constant Positive_Count_Type := P.Get (Big, Cu);
kono
parents:
diff changeset
671
kono
parents:
diff changeset
672 begin
kono
parents:
diff changeset
673 if Pos < Cut then
kono
parents:
diff changeset
674 if not P.Has_Key (Small, Cu)
kono
parents:
diff changeset
675 or else Pos /= P.Get (Small, Cu)
kono
parents:
diff changeset
676 then
kono
parents:
diff changeset
677 return False;
kono
parents:
diff changeset
678 end if;
kono
parents:
diff changeset
679
kono
parents:
diff changeset
680 elsif Pos >= Cut + Count then
kono
parents:
diff changeset
681 if not P.Has_Key (Small, Cu)
kono
parents:
diff changeset
682 or else Pos /= P.Get (Small, Cu) + Count
kono
parents:
diff changeset
683 then
kono
parents:
diff changeset
684 return False;
kono
parents:
diff changeset
685 end if;
kono
parents:
diff changeset
686
kono
parents:
diff changeset
687 else
kono
parents:
diff changeset
688 if P.Has_Key (Small, Cu) then
kono
parents:
diff changeset
689 return False;
kono
parents:
diff changeset
690 end if;
kono
parents:
diff changeset
691 end if;
kono
parents:
diff changeset
692 end;
kono
parents:
diff changeset
693 end loop;
kono
parents:
diff changeset
694
kono
parents:
diff changeset
695 return True;
kono
parents:
diff changeset
696 end P_Positions_Shifted;
kono
parents:
diff changeset
697
kono
parents:
diff changeset
698 ---------------
kono
parents:
diff changeset
699 -- Positions --
kono
parents:
diff changeset
700 ---------------
kono
parents:
diff changeset
701
kono
parents:
diff changeset
702 function Positions (Container : Map) return P.Map is
kono
parents:
diff changeset
703 I : Count_Type := 1;
kono
parents:
diff changeset
704 Position : Count_Type := Container.First;
kono
parents:
diff changeset
705 R : P.Map;
kono
parents:
diff changeset
706
kono
parents:
diff changeset
707 begin
kono
parents:
diff changeset
708 -- Can't use First, Next or Element here, since they depend on models
kono
parents:
diff changeset
709 -- for their postconditions.
kono
parents:
diff changeset
710
kono
parents:
diff changeset
711 while Position /= 0 loop
kono
parents:
diff changeset
712 R := P.Add (R, (Node => Position), I);
kono
parents:
diff changeset
713 pragma Assert (P.Length (R) = I);
kono
parents:
diff changeset
714 Position := Tree_Operations.Next (Container, Position);
kono
parents:
diff changeset
715 I := I + 1;
kono
parents:
diff changeset
716 end loop;
kono
parents:
diff changeset
717
kono
parents:
diff changeset
718 return R;
kono
parents:
diff changeset
719 end Positions;
kono
parents:
diff changeset
720
kono
parents:
diff changeset
721 end Formal_Model;
kono
parents:
diff changeset
722
kono
parents:
diff changeset
723 ----------
kono
parents:
diff changeset
724 -- Free --
kono
parents:
diff changeset
725 ----------
kono
parents:
diff changeset
726
kono
parents:
diff changeset
727 procedure Free
kono
parents:
diff changeset
728 (Tree : in out Map;
kono
parents:
diff changeset
729 X : Count_Type)
kono
parents:
diff changeset
730 is
kono
parents:
diff changeset
731 begin
kono
parents:
diff changeset
732 Tree.Nodes (X).Has_Element := False;
kono
parents:
diff changeset
733 Tree_Operations.Free (Tree, X);
kono
parents:
diff changeset
734 end Free;
kono
parents:
diff changeset
735
kono
parents:
diff changeset
736 ----------------------
kono
parents:
diff changeset
737 -- Generic_Allocate --
kono
parents:
diff changeset
738 ----------------------
kono
parents:
diff changeset
739
kono
parents:
diff changeset
740 procedure Generic_Allocate
kono
parents:
diff changeset
741 (Tree : in out Tree_Types.Tree_Type'Class;
kono
parents:
diff changeset
742 Node : out Count_Type)
kono
parents:
diff changeset
743 is
kono
parents:
diff changeset
744 procedure Allocate is
kono
parents:
diff changeset
745 new Tree_Operations.Generic_Allocate (Set_Element);
kono
parents:
diff changeset
746 begin
kono
parents:
diff changeset
747 Allocate (Tree, Node);
kono
parents:
diff changeset
748 Tree.Nodes (Node).Has_Element := True;
kono
parents:
diff changeset
749 end Generic_Allocate;
kono
parents:
diff changeset
750
kono
parents:
diff changeset
751 -----------------
kono
parents:
diff changeset
752 -- Has_Element --
kono
parents:
diff changeset
753 -----------------
kono
parents:
diff changeset
754
kono
parents:
diff changeset
755 function Has_Element (Container : Map; Position : Cursor) return Boolean is
kono
parents:
diff changeset
756 begin
kono
parents:
diff changeset
757 if Position.Node = 0 then
kono
parents:
diff changeset
758 return False;
kono
parents:
diff changeset
759 end if;
kono
parents:
diff changeset
760
kono
parents:
diff changeset
761 return Container.Nodes (Position.Node).Has_Element;
kono
parents:
diff changeset
762 end Has_Element;
kono
parents:
diff changeset
763
kono
parents:
diff changeset
764 -------------
kono
parents:
diff changeset
765 -- Include --
kono
parents:
diff changeset
766 -------------
kono
parents:
diff changeset
767
kono
parents:
diff changeset
768 procedure Include
kono
parents:
diff changeset
769 (Container : in out Map;
kono
parents:
diff changeset
770 Key : Key_Type;
kono
parents:
diff changeset
771 New_Item : Element_Type)
kono
parents:
diff changeset
772 is
kono
parents:
diff changeset
773 Position : Cursor;
kono
parents:
diff changeset
774 Inserted : Boolean;
kono
parents:
diff changeset
775
kono
parents:
diff changeset
776 begin
kono
parents:
diff changeset
777 Insert (Container, Key, New_Item, Position, Inserted);
kono
parents:
diff changeset
778
kono
parents:
diff changeset
779 if not Inserted then
kono
parents:
diff changeset
780 declare
kono
parents:
diff changeset
781 N : Node_Type renames Container.Nodes (Position.Node);
kono
parents:
diff changeset
782 begin
kono
parents:
diff changeset
783 N.Key := Key;
kono
parents:
diff changeset
784 N.Element := New_Item;
kono
parents:
diff changeset
785 end;
kono
parents:
diff changeset
786 end if;
kono
parents:
diff changeset
787 end Include;
kono
parents:
diff changeset
788
kono
parents:
diff changeset
789 procedure Insert
kono
parents:
diff changeset
790 (Container : in out Map;
kono
parents:
diff changeset
791 Key : Key_Type;
kono
parents:
diff changeset
792 New_Item : Element_Type;
kono
parents:
diff changeset
793 Position : out Cursor;
kono
parents:
diff changeset
794 Inserted : out Boolean)
kono
parents:
diff changeset
795 is
kono
parents:
diff changeset
796 function New_Node return Node_Access;
kono
parents:
diff changeset
797 -- Comment ???
kono
parents:
diff changeset
798
kono
parents:
diff changeset
799 procedure Insert_Post is
kono
parents:
diff changeset
800 new Key_Ops.Generic_Insert_Post (New_Node);
kono
parents:
diff changeset
801
kono
parents:
diff changeset
802 procedure Insert_Sans_Hint is
kono
parents:
diff changeset
803 new Key_Ops.Generic_Conditional_Insert (Insert_Post);
kono
parents:
diff changeset
804
kono
parents:
diff changeset
805 --------------
kono
parents:
diff changeset
806 -- New_Node --
kono
parents:
diff changeset
807 --------------
kono
parents:
diff changeset
808
kono
parents:
diff changeset
809 function New_Node return Node_Access is
kono
parents:
diff changeset
810 procedure Initialize (Node : in out Node_Type);
kono
parents:
diff changeset
811 procedure Allocate_Node is new Generic_Allocate (Initialize);
kono
parents:
diff changeset
812
kono
parents:
diff changeset
813 procedure Initialize (Node : in out Node_Type) is
kono
parents:
diff changeset
814 begin
kono
parents:
diff changeset
815 Node.Key := Key;
kono
parents:
diff changeset
816 Node.Element := New_Item;
kono
parents:
diff changeset
817 end Initialize;
kono
parents:
diff changeset
818
kono
parents:
diff changeset
819 X : Node_Access;
kono
parents:
diff changeset
820
kono
parents:
diff changeset
821 begin
kono
parents:
diff changeset
822 Allocate_Node (Container, X);
kono
parents:
diff changeset
823 return X;
kono
parents:
diff changeset
824 end New_Node;
kono
parents:
diff changeset
825
kono
parents:
diff changeset
826 -- Start of processing for Insert
kono
parents:
diff changeset
827
kono
parents:
diff changeset
828 begin
kono
parents:
diff changeset
829 Insert_Sans_Hint
kono
parents:
diff changeset
830 (Container,
kono
parents:
diff changeset
831 Key,
kono
parents:
diff changeset
832 Position.Node,
kono
parents:
diff changeset
833 Inserted);
kono
parents:
diff changeset
834 end Insert;
kono
parents:
diff changeset
835
kono
parents:
diff changeset
836 procedure Insert
kono
parents:
diff changeset
837 (Container : in out Map;
kono
parents:
diff changeset
838 Key : Key_Type;
kono
parents:
diff changeset
839 New_Item : Element_Type)
kono
parents:
diff changeset
840 is
kono
parents:
diff changeset
841 Position : Cursor;
kono
parents:
diff changeset
842 Inserted : Boolean;
kono
parents:
diff changeset
843
kono
parents:
diff changeset
844 begin
kono
parents:
diff changeset
845 Insert (Container, Key, New_Item, Position, Inserted);
kono
parents:
diff changeset
846
kono
parents:
diff changeset
847 if not Inserted then
kono
parents:
diff changeset
848 raise Constraint_Error with "key already in map";
kono
parents:
diff changeset
849 end if;
kono
parents:
diff changeset
850 end Insert;
kono
parents:
diff changeset
851
kono
parents:
diff changeset
852 --------------
kono
parents:
diff changeset
853 -- Is_Empty --
kono
parents:
diff changeset
854 --------------
kono
parents:
diff changeset
855
kono
parents:
diff changeset
856 function Is_Empty (Container : Map) return Boolean is
kono
parents:
diff changeset
857 begin
kono
parents:
diff changeset
858 return Length (Container) = 0;
kono
parents:
diff changeset
859 end Is_Empty;
kono
parents:
diff changeset
860
kono
parents:
diff changeset
861 -------------------------
kono
parents:
diff changeset
862 -- Is_Greater_Key_Node --
kono
parents:
diff changeset
863 -------------------------
kono
parents:
diff changeset
864
kono
parents:
diff changeset
865 function Is_Greater_Key_Node
kono
parents:
diff changeset
866 (Left : Key_Type;
kono
parents:
diff changeset
867 Right : Node_Type) return Boolean
kono
parents:
diff changeset
868 is
kono
parents:
diff changeset
869 begin
kono
parents:
diff changeset
870 -- k > node same as node < k
kono
parents:
diff changeset
871
kono
parents:
diff changeset
872 return Right.Key < Left;
kono
parents:
diff changeset
873 end Is_Greater_Key_Node;
kono
parents:
diff changeset
874
kono
parents:
diff changeset
875 ----------------------
kono
parents:
diff changeset
876 -- Is_Less_Key_Node --
kono
parents:
diff changeset
877 ----------------------
kono
parents:
diff changeset
878
kono
parents:
diff changeset
879 function Is_Less_Key_Node
kono
parents:
diff changeset
880 (Left : Key_Type;
kono
parents:
diff changeset
881 Right : Node_Type) return Boolean
kono
parents:
diff changeset
882 is
kono
parents:
diff changeset
883 begin
kono
parents:
diff changeset
884 return Left < Right.Key;
kono
parents:
diff changeset
885 end Is_Less_Key_Node;
kono
parents:
diff changeset
886
kono
parents:
diff changeset
887 ---------
kono
parents:
diff changeset
888 -- Key --
kono
parents:
diff changeset
889 ---------
kono
parents:
diff changeset
890
kono
parents:
diff changeset
891 function Key (Container : Map; Position : Cursor) return Key_Type is
kono
parents:
diff changeset
892 begin
kono
parents:
diff changeset
893 if not Has_Element (Container, Position) then
kono
parents:
diff changeset
894 raise Constraint_Error with
kono
parents:
diff changeset
895 "Position cursor of function Key has no element";
kono
parents:
diff changeset
896 end if;
kono
parents:
diff changeset
897
kono
parents:
diff changeset
898 pragma Assert (Vet (Container, Position.Node),
kono
parents:
diff changeset
899 "Position cursor of function Key is bad");
kono
parents:
diff changeset
900
kono
parents:
diff changeset
901 return Container.Nodes (Position.Node).Key;
kono
parents:
diff changeset
902 end Key;
kono
parents:
diff changeset
903
kono
parents:
diff changeset
904 ----------
kono
parents:
diff changeset
905 -- Last --
kono
parents:
diff changeset
906 ----------
kono
parents:
diff changeset
907
kono
parents:
diff changeset
908 function Last (Container : Map) return Cursor is
kono
parents:
diff changeset
909 begin
kono
parents:
diff changeset
910 if Length (Container) = 0 then
kono
parents:
diff changeset
911 return No_Element;
kono
parents:
diff changeset
912 end if;
kono
parents:
diff changeset
913
kono
parents:
diff changeset
914 return (Node => Container.Last);
kono
parents:
diff changeset
915 end Last;
kono
parents:
diff changeset
916
kono
parents:
diff changeset
917 ------------------
kono
parents:
diff changeset
918 -- Last_Element --
kono
parents:
diff changeset
919 ------------------
kono
parents:
diff changeset
920
kono
parents:
diff changeset
921 function Last_Element (Container : Map) return Element_Type is
kono
parents:
diff changeset
922 begin
kono
parents:
diff changeset
923 if Is_Empty (Container) then
kono
parents:
diff changeset
924 raise Constraint_Error with "map is empty";
kono
parents:
diff changeset
925 end if;
kono
parents:
diff changeset
926
kono
parents:
diff changeset
927 return Container.Nodes (Last (Container).Node).Element;
kono
parents:
diff changeset
928 end Last_Element;
kono
parents:
diff changeset
929
kono
parents:
diff changeset
930 --------------
kono
parents:
diff changeset
931 -- Last_Key --
kono
parents:
diff changeset
932 --------------
kono
parents:
diff changeset
933
kono
parents:
diff changeset
934 function Last_Key (Container : Map) return Key_Type is
kono
parents:
diff changeset
935 begin
kono
parents:
diff changeset
936 if Is_Empty (Container) then
kono
parents:
diff changeset
937 raise Constraint_Error with "map is empty";
kono
parents:
diff changeset
938 end if;
kono
parents:
diff changeset
939
kono
parents:
diff changeset
940 return Container.Nodes (Last (Container).Node).Key;
kono
parents:
diff changeset
941 end Last_Key;
kono
parents:
diff changeset
942
kono
parents:
diff changeset
943 --------------
kono
parents:
diff changeset
944 -- Left_Son --
kono
parents:
diff changeset
945 --------------
kono
parents:
diff changeset
946
kono
parents:
diff changeset
947 function Left_Son (Node : Node_Type) return Count_Type is
kono
parents:
diff changeset
948 begin
kono
parents:
diff changeset
949 return Node.Left;
kono
parents:
diff changeset
950 end Left_Son;
kono
parents:
diff changeset
951
kono
parents:
diff changeset
952 ------------
kono
parents:
diff changeset
953 -- Length --
kono
parents:
diff changeset
954 ------------
kono
parents:
diff changeset
955
kono
parents:
diff changeset
956 function Length (Container : Map) return Count_Type is
kono
parents:
diff changeset
957 begin
kono
parents:
diff changeset
958 return Container.Length;
kono
parents:
diff changeset
959 end Length;
kono
parents:
diff changeset
960
kono
parents:
diff changeset
961 ----------
kono
parents:
diff changeset
962 -- Move --
kono
parents:
diff changeset
963 ----------
kono
parents:
diff changeset
964
kono
parents:
diff changeset
965 procedure Move (Target : in out Map; Source : in out Map) is
kono
parents:
diff changeset
966 NN : Tree_Types.Nodes_Type renames Source.Nodes;
kono
parents:
diff changeset
967 X : Node_Access;
kono
parents:
diff changeset
968
kono
parents:
diff changeset
969 begin
kono
parents:
diff changeset
970 if Target'Address = Source'Address then
kono
parents:
diff changeset
971 return;
kono
parents:
diff changeset
972 end if;
kono
parents:
diff changeset
973
kono
parents:
diff changeset
974 if Target.Capacity < Length (Source) then
kono
parents:
diff changeset
975 raise Constraint_Error with -- ???
kono
parents:
diff changeset
976 "Source length exceeds Target capacity";
kono
parents:
diff changeset
977 end if;
kono
parents:
diff changeset
978
kono
parents:
diff changeset
979 Clear (Target);
kono
parents:
diff changeset
980
kono
parents:
diff changeset
981 loop
kono
parents:
diff changeset
982 X := First (Source).Node;
kono
parents:
diff changeset
983 exit when X = 0;
kono
parents:
diff changeset
984
kono
parents:
diff changeset
985 -- Here we insert a copy of the source element into the target, and
kono
parents:
diff changeset
986 -- then delete the element from the source. Another possibility is
kono
parents:
diff changeset
987 -- that delete it first (and hang onto its index), then insert it.
kono
parents:
diff changeset
988 -- ???
kono
parents:
diff changeset
989
kono
parents:
diff changeset
990 Insert (Target, NN (X).Key, NN (X).Element); -- optimize???
kono
parents:
diff changeset
991
kono
parents:
diff changeset
992 Tree_Operations.Delete_Node_Sans_Free (Source, X);
kono
parents:
diff changeset
993 Formal_Ordered_Maps.Free (Source, X);
kono
parents:
diff changeset
994 end loop;
kono
parents:
diff changeset
995 end Move;
kono
parents:
diff changeset
996
kono
parents:
diff changeset
997 ----------
kono
parents:
diff changeset
998 -- Next --
kono
parents:
diff changeset
999 ----------
kono
parents:
diff changeset
1000
kono
parents:
diff changeset
1001 procedure Next (Container : Map; Position : in out Cursor) is
kono
parents:
diff changeset
1002 begin
kono
parents:
diff changeset
1003 Position := Next (Container, Position);
kono
parents:
diff changeset
1004 end Next;
kono
parents:
diff changeset
1005
kono
parents:
diff changeset
1006 function Next (Container : Map; Position : Cursor) return Cursor is
kono
parents:
diff changeset
1007 begin
kono
parents:
diff changeset
1008 if Position = No_Element then
kono
parents:
diff changeset
1009 return No_Element;
kono
parents:
diff changeset
1010 end if;
kono
parents:
diff changeset
1011
kono
parents:
diff changeset
1012 if not Has_Element (Container, Position) then
kono
parents:
diff changeset
1013 raise Constraint_Error;
kono
parents:
diff changeset
1014 end if;
kono
parents:
diff changeset
1015
kono
parents:
diff changeset
1016 pragma Assert (Vet (Container, Position.Node),
kono
parents:
diff changeset
1017 "bad cursor in Next");
kono
parents:
diff changeset
1018
kono
parents:
diff changeset
1019 return (Node => Tree_Operations.Next (Container, Position.Node));
kono
parents:
diff changeset
1020 end Next;
kono
parents:
diff changeset
1021
kono
parents:
diff changeset
1022 ------------
kono
parents:
diff changeset
1023 -- Parent --
kono
parents:
diff changeset
1024 ------------
kono
parents:
diff changeset
1025
kono
parents:
diff changeset
1026 function Parent (Node : Node_Type) return Count_Type is
kono
parents:
diff changeset
1027 begin
kono
parents:
diff changeset
1028 return Node.Parent;
kono
parents:
diff changeset
1029 end Parent;
kono
parents:
diff changeset
1030
kono
parents:
diff changeset
1031 --------------
kono
parents:
diff changeset
1032 -- Previous --
kono
parents:
diff changeset
1033 --------------
kono
parents:
diff changeset
1034
kono
parents:
diff changeset
1035 procedure Previous (Container : Map; Position : in out Cursor) is
kono
parents:
diff changeset
1036 begin
kono
parents:
diff changeset
1037 Position := Previous (Container, Position);
kono
parents:
diff changeset
1038 end Previous;
kono
parents:
diff changeset
1039
kono
parents:
diff changeset
1040 function Previous (Container : Map; Position : Cursor) return Cursor is
kono
parents:
diff changeset
1041 begin
kono
parents:
diff changeset
1042 if Position = No_Element then
kono
parents:
diff changeset
1043 return No_Element;
kono
parents:
diff changeset
1044 end if;
kono
parents:
diff changeset
1045
kono
parents:
diff changeset
1046 if not Has_Element (Container, Position) then
kono
parents:
diff changeset
1047 raise Constraint_Error;
kono
parents:
diff changeset
1048 end if;
kono
parents:
diff changeset
1049
kono
parents:
diff changeset
1050 pragma Assert (Vet (Container, Position.Node),
kono
parents:
diff changeset
1051 "bad cursor in Previous");
kono
parents:
diff changeset
1052
kono
parents:
diff changeset
1053 declare
kono
parents:
diff changeset
1054 Node : constant Count_Type :=
kono
parents:
diff changeset
1055 Tree_Operations.Previous (Container, Position.Node);
kono
parents:
diff changeset
1056
kono
parents:
diff changeset
1057 begin
kono
parents:
diff changeset
1058 if Node = 0 then
kono
parents:
diff changeset
1059 return No_Element;
kono
parents:
diff changeset
1060 end if;
kono
parents:
diff changeset
1061
kono
parents:
diff changeset
1062 return (Node => Node);
kono
parents:
diff changeset
1063 end;
kono
parents:
diff changeset
1064 end Previous;
kono
parents:
diff changeset
1065
kono
parents:
diff changeset
1066 -------------
kono
parents:
diff changeset
1067 -- Replace --
kono
parents:
diff changeset
1068 -------------
kono
parents:
diff changeset
1069
kono
parents:
diff changeset
1070 procedure Replace
kono
parents:
diff changeset
1071 (Container : in out Map;
kono
parents:
diff changeset
1072 Key : Key_Type;
kono
parents:
diff changeset
1073 New_Item : Element_Type)
kono
parents:
diff changeset
1074 is
kono
parents:
diff changeset
1075 begin
kono
parents:
diff changeset
1076 declare
kono
parents:
diff changeset
1077 Node : constant Node_Access := Key_Ops.Find (Container, Key);
kono
parents:
diff changeset
1078
kono
parents:
diff changeset
1079 begin
kono
parents:
diff changeset
1080 if Node = 0 then
kono
parents:
diff changeset
1081 raise Constraint_Error with "key not in map";
kono
parents:
diff changeset
1082 end if;
kono
parents:
diff changeset
1083
kono
parents:
diff changeset
1084 declare
kono
parents:
diff changeset
1085 N : Node_Type renames Container.Nodes (Node);
kono
parents:
diff changeset
1086 begin
kono
parents:
diff changeset
1087 N.Key := Key;
kono
parents:
diff changeset
1088 N.Element := New_Item;
kono
parents:
diff changeset
1089 end;
kono
parents:
diff changeset
1090 end;
kono
parents:
diff changeset
1091 end Replace;
kono
parents:
diff changeset
1092
kono
parents:
diff changeset
1093 ---------------------
kono
parents:
diff changeset
1094 -- Replace_Element --
kono
parents:
diff changeset
1095 ---------------------
kono
parents:
diff changeset
1096
kono
parents:
diff changeset
1097 procedure Replace_Element
kono
parents:
diff changeset
1098 (Container : in out Map;
kono
parents:
diff changeset
1099 Position : Cursor;
kono
parents:
diff changeset
1100 New_Item : Element_Type)
kono
parents:
diff changeset
1101 is
kono
parents:
diff changeset
1102 begin
kono
parents:
diff changeset
1103 if not Has_Element (Container, Position) then
kono
parents:
diff changeset
1104 raise Constraint_Error with
kono
parents:
diff changeset
1105 "Position cursor of Replace_Element has no element";
kono
parents:
diff changeset
1106 end if;
kono
parents:
diff changeset
1107
kono
parents:
diff changeset
1108 pragma Assert (Vet (Container, Position.Node),
kono
parents:
diff changeset
1109 "Position cursor of Replace_Element is bad");
kono
parents:
diff changeset
1110
kono
parents:
diff changeset
1111 Container.Nodes (Position.Node).Element := New_Item;
kono
parents:
diff changeset
1112 end Replace_Element;
kono
parents:
diff changeset
1113
kono
parents:
diff changeset
1114 ---------------
kono
parents:
diff changeset
1115 -- Right_Son --
kono
parents:
diff changeset
1116 ---------------
kono
parents:
diff changeset
1117
kono
parents:
diff changeset
1118 function Right_Son (Node : Node_Type) return Count_Type is
kono
parents:
diff changeset
1119 begin
kono
parents:
diff changeset
1120 return Node.Right;
kono
parents:
diff changeset
1121 end Right_Son;
kono
parents:
diff changeset
1122
kono
parents:
diff changeset
1123 ---------------
kono
parents:
diff changeset
1124 -- Set_Color --
kono
parents:
diff changeset
1125 ---------------
kono
parents:
diff changeset
1126
kono
parents:
diff changeset
1127 procedure Set_Color (Node : in out Node_Type; Color : Color_Type) is
kono
parents:
diff changeset
1128 begin
kono
parents:
diff changeset
1129 Node.Color := Color;
kono
parents:
diff changeset
1130 end Set_Color;
kono
parents:
diff changeset
1131
kono
parents:
diff changeset
1132 --------------
kono
parents:
diff changeset
1133 -- Set_Left --
kono
parents:
diff changeset
1134 --------------
kono
parents:
diff changeset
1135
kono
parents:
diff changeset
1136 procedure Set_Left (Node : in out Node_Type; Left : Count_Type) is
kono
parents:
diff changeset
1137 begin
kono
parents:
diff changeset
1138 Node.Left := Left;
kono
parents:
diff changeset
1139 end Set_Left;
kono
parents:
diff changeset
1140
kono
parents:
diff changeset
1141 ----------------
kono
parents:
diff changeset
1142 -- Set_Parent --
kono
parents:
diff changeset
1143 ----------------
kono
parents:
diff changeset
1144
kono
parents:
diff changeset
1145 procedure Set_Parent (Node : in out Node_Type; Parent : Count_Type) is
kono
parents:
diff changeset
1146 begin
kono
parents:
diff changeset
1147 Node.Parent := Parent;
kono
parents:
diff changeset
1148 end Set_Parent;
kono
parents:
diff changeset
1149
kono
parents:
diff changeset
1150 ---------------
kono
parents:
diff changeset
1151 -- Set_Right --
kono
parents:
diff changeset
1152 ---------------
kono
parents:
diff changeset
1153
kono
parents:
diff changeset
1154 procedure Set_Right (Node : in out Node_Type; Right : Count_Type) is
kono
parents:
diff changeset
1155 begin
kono
parents:
diff changeset
1156 Node.Right := Right;
kono
parents:
diff changeset
1157 end Set_Right;
kono
parents:
diff changeset
1158
kono
parents:
diff changeset
1159 end Ada.Containers.Formal_Ordered_Maps;