summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorRoman Smrž <roman.smrz@seznam.cz>2020-08-26 21:30:42 +0200
committerRoman Smrž <roman.smrz@seznam.cz>2020-08-26 21:30:53 +0200
commit0f9f0fc472de3ae8b4a2ae3ed503a0872fc94b2b (patch)
tree159daa98dd311fe835fcd4f1ec5210adb22edf9c
parenta4437f0479a721aeebac305e403b88b18a5f7d5f (diff)
wip: RefMapref-map
-rw-r--r--src/RefMap.hs85
1 files changed, 85 insertions, 0 deletions
diff --git a/src/RefMap.hs b/src/RefMap.hs
new file mode 100644
index 0000000..500ea4b
--- /dev/null
+++ b/src/RefMap.hs
@@ -0,0 +1,85 @@
+module RefMap (
+ RefMap,
+
+ null,
+ size,
+ member,
+ notMember,
+
+ fromList,
+ toList,
+ empty,
+
+ lookup,
+ insert,
+ insertNew,
+ elems,
+ delete,
+ adjust,
+ assocs,
+) where
+
+import Storage.Internal (RefDigest, Ref)
+
+import Data.IntMap (IntMap)
+import qualified Data.IntMap as IM
+
+data RefMap a = IntMap [(RefDigest, a)]
+
+instance Functor RefMap where
+ fmap f (RefMap im) = RefMap (fmap f im)
+
+instance Foldable RefMap where
+ foldMap f (RefMap im) = foldMap f im
+
+instance Traversable RefMap where
+ traverse f (RefMap im) = RefMap <$> traverse f im
+
+
+splitRef :: Ref -> (Int, Digest)
+splitRef r =
+
+
+null :: RefMap a -> Bool
+null (RefMap im) = IM.null im
+
+size :: RefMap a -> Int
+size (RefMap im) = sum $ map length $ IM.elems im
+
+member :: Ref -> RefMap a -> Bool
+member r (RefMap im) | Just xs <- IM.lookup i im = any ((==d) . fst) xs
+ | otherwise = False
+ where (i, d) = splitRef r
+
+notMember :: (Integral i) => i -> RefMap a -> Bool
+notMember i (RefMap im) = IM.notMember (fromIntegral i) im
+
+fromList :: (Integral i) => [(i, a)] -> RefMap a
+fromList xs = IDMap (maximum (map fst xs) + 1) $ IM.fromList $ map (\(i,x) -> (fromIntegral i, x)) xs
+
+toList :: (Integral i) => RefMap a -> [(i, a)]
+toList (RefMap im) = map (\(i,x) -> (fromIntegral i, x)) $ IM.toList im
+
+empty :: (Integral i) => RefMap a
+empty = IDMap 1 IM.empty
+
+lookup :: (Integral i, Monad m) => i -> RefMap a -> m a
+lookup i (RefMap im) = maybe (fail "IDMap.lookup: item not found") return $ IM.lookup (fromIntegral i) im
+
+insert :: (Integral i) => i -> a -> RefMap a -> RefMap a
+insert i x (RefMap im) = IDMap (max n (i+1)) (IM.insert (fromIntegral i) x im)
+
+insertNew :: (Integral i) => a -> RefMap a -> (RefMap a, i)
+insertNew x (RefMap im) = (IDMap (n+1) $ IM.insert (fromIntegral n) x im, n)
+
+elems :: RefMap a -> [a]
+elems (RefMap im) = IM.elems im
+
+delete :: (Integral i) => i -> RefMap a -> RefMap a
+delete i (RefMap im) = RefMap $ IM.delete (fromIntegral i) im
+
+adjust :: (Integral i) => (a -> a) -> i -> RefMap a -> RefMap a
+adjust f i (RefMap im) = RefMap $ IM.adjust f (fromIntegral i) im
+
+assocs :: (Integral i) => RefMap a -> [(i,a)]
+assocs (RefMap im) = map (\(i,x) -> (fromIntegral i, x)) $ IM.assocs im