src/Pure/General/heap.ML
author wenzelm
Wed, 31 Dec 2008 18:53:16 +0100
changeset 29270 0eade173f77e
parent 28581 6cd2e5d5c6d0
child 29606 fedb8be05f24
permissions -rw-r--r--
moved old add_type_XXX, add_term_XXX etc. to structure OldTerm;
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
     1
(*  Title:      Pure/General/heap.ML
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
     2
    ID:         $Id$
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
     3
    Author:     Markus Wenzel, TU Muenchen
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
     4
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
     5
Heaps over linearly ordered types.  See also Chris Okasaki: "Purely
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
     6
Functional Data Structures" (Chapter 3), Cambridge University Press,
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
     7
1998.
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
     8
*)
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
     9
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    10
signature HEAP =
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    11
sig
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    12
  type elem
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    13
  type T
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    14
  val empty: T
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    15
  val is_empty: T -> bool
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    16
  val merge: T * T -> T
23179
8db2b22257bd insert: canonical argument order;
wenzelm
parents: 18134
diff changeset
    17
  val insert: elem -> T -> T
28581
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    18
  val min: T -> elem            (*exception Empty*)
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    19
  val delete_min: T -> T        (*exception Empty*)
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    20
  val min_elem: T -> elem * T   (*exception Empty*)
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    21
  val upto: elem -> T -> elem list * T
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    22
end;
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    23
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    24
functor HeapFun(type elem val ord: elem * elem -> order): HEAP =
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    25
struct
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    26
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    27
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    28
(* datatype heap *)
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    29
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    30
type elem = elem;
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    31
datatype T = Empty | Heap of int * elem * T * T;
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    32
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    33
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    34
(* empty heaps *)
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    35
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    36
val empty = Empty;
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    37
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    38
fun is_empty Empty = true
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    39
  | is_empty (Heap _) = false;
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    40
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    41
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    42
(* build heaps *)
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    43
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    44
local
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    45
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    46
fun rank Empty = 0
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    47
  | rank (Heap (r, _, _, _)) = r;
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    48
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    49
fun heap x a b =
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    50
  if rank a >= rank b then Heap (rank b + 1, x, a, b)
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    51
  else Heap (rank a + 1, x, b, a);
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    52
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    53
in
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    54
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    55
fun merge (h, Empty) = h
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    56
  | merge (Empty, h) = h
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    57
  | merge (h1 as Heap (_, x1, a1, b1), h2 as Heap (_, x2, a2, b2)) =
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    58
      (case ord (x1, x2) of
14472
cba7c0a3ffb3 Removing the datatype declaration of "order" allows the standard General.order
paulson
parents: 9413
diff changeset
    59
        GREATER => heap x2 a2 (merge (h1, b2))
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    60
      | _ => heap x1 a1 (merge (b1, h2)));
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    61
23179
8db2b22257bd insert: canonical argument order;
wenzelm
parents: 18134
diff changeset
    62
fun insert x h = merge (Heap (1, x, Empty, Empty), h);
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    63
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    64
end;
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    65
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    66
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    67
(* minimum element *)
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    68
18134
6450591da9f0 use existing exeption Empty;
wenzelm
parents: 14981
diff changeset
    69
fun min Empty = raise List.Empty
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    70
  | min (Heap (_, x, _, _)) = x;
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    71
18134
6450591da9f0 use existing exeption Empty;
wenzelm
parents: 14981
diff changeset
    72
fun delete_min Empty = raise List.Empty
9413
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    73
  | delete_min (Heap (_, _, a, b)) = merge (a, b);
ba209591a8d4 assimilated;
wenzelm
parents: 9095
diff changeset
    74
28581
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    75
fun min_elem h = (min h, delete_min h);
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    76
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    77
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    78
(* initial interval *)
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    79
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    80
nonfix upto;
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    81
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    82
fun upto _ (h as Empty) = ([], h)
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    83
  | upto limit (h as Heap (_, x, a, b)) =
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    84
      (case ord (x, limit) of
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    85
        GREATER => ([], h)
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    86
      | _ => upto limit (delete_min h) |>> cons x);
6cd2e5d5c6d0 added min_elem, upto;
wenzelm
parents: 23179
diff changeset
    87
9095
3b26cc949016 new module for heaps
paulson
parents:
diff changeset
    88
end;