set_incl.sa
Generated by gen_html_sa_files from ICSI. Contact gomes@icsi.berkeley.edu for details
-------------------------> GNU Sather - sourcefile <-------------------------
-- Copyright (C) 2000 by K Hopper, University of Waikato, New Zealand --
-- This file is part of the GNU Sather library. It is free software; you may --
-- redistribute and/or modify it under the terms of the GNU Library General --
-- Public License (LGPL) as published by the Free Software Foundation; --
-- either version 2 of the license, or (at your option) any later version. --
-- This library is distributed in the hope that it will be useful, but --
-- WITHOUT ANY WARRANTY without even the implied warranty of MERCHANTABILITY --
-- or FITNESS FOR A PARTICULAR PURPOSE. See Doc/LGPL for more details. --
-- The license text is also available from: Free Software Foundation, Inc., --
-- 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA --
--------------> Please email comments to <bug-sather@gnu.org> <--------------
partial class RO_SET_INCL{ELT} < $RO_SET{ELT}
partial class RO_SET_INCL{ELT} < $RO_SET{ELT} is
-- This partial class corresponding to $RO_SET{ELT} implements other
-- functions in terms of has and elt!
-- Version 1.2 Nov 98. Copyright K Hopper, U of Waikato
-- Development History
-- -------------------
-- Date Who By Detail
-- ---- ------ ------
-- 13 Jul 96 bg Original
-- 4 Apr 97 kh Changed for style conformity
-- 12 Nov 98 kh Revised for 1.2, added pre/post conditions.
include CONTAINER{ELT}
contains -> ;
stub elt! : ELT ;
-- This iter yields all of the elements of the set in an arbitrary order.
stub copy : SAME ;
-- This routine returns a new set which is an exact copy of self.
stub insert(
elem : ELT
) : SAME ;
-- This routine inserts the new element into the set before returning
-- the resultant set.
stub delete(
elem : ELT
) : SAME ;
-- This routine returns a set which has had an element which is element
-- equal to the argument deleted.
stub create : SAME ;
-- This routine creates and returns a new empty set.
create(
arg : $ELT{ELT}
) : SAME is
-- This routine creates a new set and gives it the contents of arg.
me : SAME := create ;
loop
me := me.insert(arg.elt!)
end ;
return me
end ;
create(
arg : ARRAY{ELT}
) : SAME is
-- This routine creates a new set from the elements of the array arg.
-- NOTE The reason for having a separate routine for this case is to permit
-- type inference to be used when needed.
me : SAME := create ;
loop
me := me.insert(arg.elt!)
end ;
return me
end ;
is_empty : BOOL
pre ~void(self) is
-- This predicate returns true if and only if there are no elements in
-- self. The quit nature of an iter (elt!) is used to save counting
-- in size.
loop
elem : ELT := elt! ;
return false -- only reached if elems present!
end ;
return true
end ;
equals(
other :$RO_BAG{ELT}
) : BOOL
pre ~void(self)
and ~void(other) is
-- This predicate returns true if and only if every element of self is
-- elt_eq to an element in other and vice versa. Neither may be void.
if other.size /= size then
return false
end ;
loop
elem : ELT := other.elt! ;
if ~contains(elem) then
return false
end
end ;
loop -- now the converse test loop
if ~other.contains(elt!) then
return false
end
end ;
return true
end ;
is_subset_of(
other : $RO_BAG{ELT}
) : BOOL is
-- This predicate returns true if and only if self is a subset of other.
loop
loc_elem : ELT := elt! ;
if ~other.contains(loc_elem) then
return false
end
end ;
return true
end ;
count(
elem : ELT
) : CARD
pre true
post (contains(elem)
and (result = 1))
or (result = 0)
is
-- This routine makes special use of the fact that there is only one
-- possible 'count' if the element is there at all - this is, after all,
-- a set!
if contains(elem) then
return 1
else
return 0
end
end ;
n_unique : CARD
pre ~void(self)
post (result = size)
is
-- This orutine returns the number of unique elements in the set - which
-- is trivially equal to its size!
return size
end ;
array : ARRAY{ELT}
pre true
post void(result) -- 'cos self is void
or (result.size = size)
is
-- This routine returns the contents of the set as an array.
res : ARRAY{ELT} := ARRAY{ELT}::create(size) ;
loop
res.set!(elt!)
end ;
return res
end ;
add(
elem : ELT
) : VBAG{ELT}
pre ~void(self)
post (result.size = size + 1)
and result.contains(elem)
is
-- This routine returns a new value bag which contains, in addition to
-- all of the elements of self, the new element elem.
res : VBAG{ELT} := VBAG{ELT}::create(self) ;
return res.add(elem)
end ;
delete_all(
elem : ELT
) : SAME
pre true
post ~result.contains(elem)
is
-- This routine returns a new set containing all of the elements of self
-- except for the one element (this is a set!) equal to elem.
return delete(elem)
end ;
concat(
arg : $ELT{ELT}
) : VBAG{ELT}
pre ~void(self)
post (result.size = (size + arg.size))
is
-- This routine returns a new bag containing all of the elements of
-- self and arg. For elements that occur (only possible in arg!!) multiple
-- times, the result contains the sum of the number of occurences in self
-- and arg.
res : VBAG{ELT} := VBAG{ELT}::create(self) ;
loop
loc_elem : ELT := arg.elt! ;
res := res.add(loc_elem)
end ;
return res
end ;
union(
arg : $RO_BAG{ELT}
) : VBAG{ELT}
pre ~void(self)
post (result.size <= (size + arg.size))
is
-- This routine returns a new bag which is the union of the elements of
-- self and those of arg. For elements that occur multiple times (which can
-- only be in arg as this is a set!), the result contains the maximum number
-- of occurences in either self or arg. This definition permits the union of
-- sets to be consistent with the union of bags.
res : VBAG{ELT} := VBAG{ELT}::create(self) ;
loop
arg_elt : ELT := arg.elt! ;
if ~res.contains(arg_elt) then
res := res.add(arg_elt)
else
if arg.count(arg_elt) > res.count(arg_elt) then
res := res.add(arg_elt)
end
end
end ;
return res
end ;
union(
other : $RO_SET{ELT}
) : SAME
pre ~void(self)
post (result.size <= (size + other.size))
is
-- This routine returns a set which is the union of self and other.
-- It overloads the function in $RO_BAG which has an argument and return
-- class of $RO_BAG.
res : SAME := copy ;
loop
res := res.insert(other.elt!)
end ;
return res
end ;
intersection(
arg : $RO_BAG{ELT}
) : VBAG{ELT}
pre ~void(self)
post (result.size <= size)
is
-- This routine returns a new bag containing only those elements common
-- to self and arg. Potential multiplicity of elements in arg has no effect
-- and the result is a bag containing only one element of each 'kind'.
res : VBAG{ELT} := VBAG{ELT}::create(self) ;
loop
loc_elem : ELT := unique! ;
if ~arg.contains(loc_elem) then
res := res.delete(loc_elem)
end
end ;
return res
end ;
intersection(
other :$RO_SET{ELT}
) : SAME
pre ~void(self)
post (result.size <= size)
is
-- This routine returns a new set which is the intersection of self and
-- other. It overloads the function above for simplicity when doing type
-- inference!
res : SAME := copy ;
loop
loc_elem : ELT := elt! ;
if ~other.contains(loc_elem) then
res := res.delete(loc_elem)
end
end ;
return res
end ;
diff(
other : $RO_SET{ELT}
) : SAME
pre ~void(self)
post (result.size <= size)
is
-- This routine returns a set which is the difference of self and
-- other.
res : SAME := copy ;
loop
loc_elem : ELT := other.elt! ;
if contains(loc_elem) then
res := res.delete(loc_elem)
end
end ;
return res
end ;
sym_diff(
other : $RO_SET{ELT}
) : SAME
pre ~void(self)
post (result.size <= (size + other.size))
is
-- This routine returns a set which contains elements which are either
-- in self or in arg (but not both).
res : SAME := copy ;
loop
loc_elem : ELT := other.elt! ;
if contains(loc_elem) then
res := res.delete(loc_elem)
else
res := res.insert(loc_elem)
end
end ;
return res
end ;
end ; -- RO_SET_INCL{ELT}
partial class SET_INCL{ELT}
partial class SET_INCL{ELT} is
-- This partial class defines some of the set functions which are not
-- dependant on the implementation of the set. The most common routines
-- (union, intersect etc.) are special cased so that when the argument is
-- of type SAME there is no dispatching.
-- Version 1.2 Nov 98. Copyright K Hopper, U of Waikato
-- Development History
-- -------------------
-- Date Who By Detail
-- ---- ------ ------
-- 13 Jul 96 bg Original
-- 4 Apr 97 kh Changed for style conformity
-- 12 Nov 98 kh Revised for 1.2, added pre/post conditions/
include RO_SET_INCL{ELT} ;
create(
arg : $ELT{ELT}
) : SAME is
-- This routine creates a new set which is given the contents of arr
-- subject to the normal uniqueness rule for a set.
res : SAME := create ;
loop
res.insert(arg.elt!)
end ;
return res
end ;
create(
arr : ARRAY{ELT}
) : SAME is
-- This routine creates a new set which is given the contents of arr
-- subject to the normal uniqueness rule for a set.
res : SAME := create ;
loop
res.insert(arr.elt!)
end ;
return res
end ;
clear
pre true
post is_empty
is
-- This routine clears all of the elements of self. It does this by
-- using a separate array to avoid over-writing while reading.
elts : FLIST{ELT} := FLIST{ELT}::create ;
loop
elts := elts.push(elt!)
end ;
loop
delete(elts.elt!)
end
end ;
as_value : VSET{ELT}
pre ~void(self)
post (result.size = size)
-- and all of the elements have been copied!
is
-- This routine returns a value set which has the same contents as self.
return VSET{ELT}::create(self)
end ;
insert(
elem : ELT
) : SAME
pre ~void(self)
post result.contains(elem)
is
-- This routine returns a new set containing the elements of self and
-- the value elem (if that is not already in the set!).
res : SAME := copy ;
res.insert(elem) ;
return res
end ;
delete(
elem : ELT
) : SAME
pre ~void(self)
post ~result.contains(elem)
is
-- This routine returns a new set containing the elements of self not
-- including the value elem.
res : SAME := copy ;
res.delete(elem) ;
return res
end ;
to_union(
arg : $ELT{ELT}
)
pre ~void(self)
and ~void(arg)
post true -- (self = initial(self).union(arg))
is
-- This routine convcerts self to be the union of the initial value of
-- self with arg.
loop
loc_elem : ELT := arg.elt! ;
if ~contains(loc_elem) then
insert(loc_elem)
end
end
end ;
to_intersection(
arg : $RO_SET{ELT}
)
pre ~void(self)
and ~void(arg)
post true -- (self = initial(self).intersection(arg))
is
-- This routine converts self into the set which is the intersection of
-- the initial value of self with arg.
loop
loc_elem : ELT := elt! ;
if ~arg.contains(loc_elem) then
delete(loc_elem)
end
end
end ;
to_diff(
arg : $RO_SET{ELT}
)
pre ~void(self)
and ~void(arg)
post true -- (self = initial(self).diff(arg))
is
-- This routine modifies self to be the difference of the initial value
-- of self and arg.
loop
loc_elem : ELT := arg.elt! ;
if contains(loc_elem) then
delete(loc_elem)
end
end
end ;
to_sym_diff(
arg : $RO_SET{ELT}
)
pre ~void(self)
and ~void(arg)
post true -- (self = initial(self).sym_diff(arg))
is
-- This routine converts self into the set which is the symmetric
-- difference of the inital value of self and arg.
loop
loc_elem : ELT := arg.elt! ;
if contains(loc_elem) then
delete(loc_elem)
else
insert(loc_elem)
end
end
end ;
end ; -- SET_INCL{ELT}