/* Responsibility: * Hash Table * Usage: * (1) Object in Hashtable have to have hashCode() function and equals() function. * From historical reason, there are functional programming style and object-oriented style functions. * if function name starts chapital letter, the function is functional programming style * else the function is object-oriented style.
*/ class Hashtable issubclassof CommonDefinition
types public Contents = map Object to Object; public Bucket = mapintto Contents;
public keySet : () ==> setof Object
keySet() == let buckets = self.getBuckets() in
( dcl allKeySet : setof Object := {}; forall aContents insetrng buckets do
allKeySet := allKeySet uniondom aContents; return allKeySet
);
public put : Object * Object ==> ()
put(akey, aValue) == let buckets = self.getBuckets(),
hashcode = akey.hashCode() in
( if hashcode insetdom buckets then self.setBuckets(buckets ++ {hashcode |-> (buckets(hashcode) ++ {akey |-> aValue})}) else self.setBuckets(buckets munion {hashcode |-> {akey |-> aValue}})
);
public putAll : Contents ==> ()
putAll(aContents) == forall key insetdom aContents do ( self.put(key, aContents(key))
);
public get : Object ==> [Object]
get(key) == let buckets = self.getBuckets(),
hashcode = key.hashCode() in
( if hashcode insetdom buckets then let aContents = buckets(hashcode) in forall aKey insetdom aContents do ( if key.equals(aKey) then return aContents(aKey)
); returnnil
);
public remove : Object ==> [Object]
remove(key) == let buckets = self.getBuckets(),
hashcode = key.hashCode(),
deleteObj = self.get(key) in
( if deleteObj <> nilthen let aContents = buckets(hashcode),
newContents = aContents :-> {deleteObj} in
( self.setBuckets(buckets ++ {hashcode |-> newContents}); return deleteObj
) else returnnil
);
public valueSet : () ==> setof Object
valueSet() == let buckets = self.getBuckets() in
( dcl aValueSet : setof Object := {}; forall aContents insetrng buckets do
aValueSet := aValueSet unionrng aContents; return aValueSet
);
functions
public size : () -> nat
size() == cardself.keySet();
public contains : Object -> bool
contains(anObject) == let buckets = self.getBuckets() in exists hashcode insetdom buckets & let aContents = buckets(hashcode) in exists key insetdom aContents &
aContents(key).equals(anObject);
public containsKey : Object -> bool
containsKey(aKey) == let buckets = self.getBuckets() in exists hashcode insetdom buckets & exists key insetdom buckets(hashcode) &
aKey.equals(key);
-----------Functional Programming part
functions
staticpublic Put[@T1, @T2] :
(map @T1 to (map @T1 to @T2)) -> (@T1 -> @T1) -> @T1 -> @T2
-> (map @T1 to (map @T1 to @T2))
Put(aHashtable)(aHashCode)(aKey)(aValue) == let hashcode = aHashCode(aKey) in if hashcode insetdom aHashtable then
aHashtable ++ {hashcode |-> (aHashtable(hashcode) ++ {aKey |-> aValue})} else
aHashtable munion {hashcode |-> {aKey |-> aValue}}
;
staticpublic PutAll[@T1, @T2] :
(map @T1 to (map @T1 to @T2)) -> (@T1 -> @T1) -> (map @T1 to @T2)
-> (map @T1 to (map @T1 to @T2))
PutAll(aHashtable)(aHashCode)(aMap) ==
PutAllAux[@T1, @T2](aHashtable)(aHashCode)(aMap)(dom aMap);
staticpublic PutAllAux[@T1, @T2] :
(map @T1 to (map @T1 to @T2)) -> (@T1 -> @T1) -> (map @T1 to @T2) -> setof @T1
-> (map @T1 to (map @T1 to @T2))
PutAllAux(aHashtable)(aHashCode)(aMap)(aKeySet) == if aKeySet = {} then
aHashtable else let aKey inset aKeySet in let newHashtable = Put[@T1, @T2](aHashtable)(aHashCode)(aKey)(aMap(aKey)) in
PutAllAux[@T1, @T2](newHashtable)(aHashCode)(aMap)(aKeySet \ {aKey})
;
staticpublic Get[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> (@T1 -> @T1) -> @T1 -> [@T2]
Get(aHashtable)(aHashCode)(aKey) == let hashcode = aHashCode(aKey) in if hashcode insetdom aHashtable then Map`Get[@T1, @T2](aHashtable(hashcode))(aKey) else nil
;
staticpublic Remove[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> (@T1 -> @T1) -> @T1 -> (map @T1 to (map @T1 to @T2))
Remove(aHashtable)(aHashCode)(aKey) == let hashcode = aHashCode(aKey) in
{h |-> ({aKey} <-: aHashtable(hashcode)) | h inset {hashcode}} munion
{hashcode} <-: aHashtable ;
--Hashtableのクリアー staticpublic Clear[@T1, @T2] : () -> (map @T1 to (map @T1 to @T2))
Clear() == ({ |-> });
staticpublic KeySet[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> setof @T1
KeySet(aHashtable) == --let aMapSet = rng aHashtable, --f = lambda x : map @T1 to @T2 & dom x let aMapSet = rng aHashtable in if aMapSet <> {} then --dunion Set`fmap[map @T1 to @T2, @T2](f)(aMapSet) dunion {dom s | s inset aMapSet} else
{};
staticpublic ValueSet[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> setof @T2
ValueSet(aHashtable) == --let aMapSet = rng aHashtable, --f = lambda x : map @T1 to @T2 & rng x let aMapSet = rng aHashtable in if aMapSet <> {} then --dunion Set`fmap[map @T1 to @T2, @T2](f)(aMapSet) dunion {rng s | s inset aMapSet} else
{};
staticpublic Size[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> nat
Size(aHashtable) == card KeySet[@T1, @T2](aHashtable) ;
staticpublic IsEmpty[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> bool
IsEmpty(aHashtable) == KeySet[@T1, @T2](aHashtable) = {};
staticpublic Contains[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> @T2 -> bool
Contains(aHashtable)(aValue) == let aMapSet = rng aHashtable in if aMapSet <> {} then exists aMap inset aMapSet & aValue insetrng aMap else false;
staticpublic ContainsKey[@T1, @T2] : (map @T1 to (map @T1 to @T2)) -> @T1 -> bool
ContainsKey(aHashtable)(aKey) == let aMapSet = rng aHashtable in if aMapSet <> {} then exists aMap inset aMapSet & aKey insetdom aMap else false;
end Hashtable
¤ Dauer der Verarbeitung: 0.18 Sekunden
(vorverarbeitet)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung ist noch experimentell.