-- |
-- Module     : Simulation.Aivika.Trans.DoubleLinkedList
-- Copyright  : Copyright (c) 2009-2017, David Sorokin <david.sorokin@gmail.com>
-- License    : BSD3
-- Maintainer : David Sorokin <david.sorokin@gmail.com>
-- Stability  : experimental
-- Tested with: GHC 8.0.1
--
-- An imperative double-linked list.
--
module Simulation.Aivika.Trans.DoubleLinkedList 
       (DoubleLinkedList, 
        listNull, 
        listCount,
        newList, 
        listInsertFirst,
        listAddLast,
        listRemoveFirst,
        listRemoveLast,
        listRemove,
        listRemoveBy,
        listContains,
        listContainsBy,
        listFirst,
        listLast,
        clearList,
        freezeList) where 

import Data.Maybe
import Data.Functor

import Control.Monad

import Simulation.Aivika.Trans.Ref.Base
import Simulation.Aivika.Trans.Simulation
import Simulation.Aivika.Trans.Event

-- | A cell of the double-linked list.
data DoubleLinkedItem m a = 
  DoubleLinkedItem { DoubleLinkedItem m a -> a
itemVal  :: a,
                     DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev :: Ref m (Maybe (DoubleLinkedItem m a)),
                     DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext :: Ref m (Maybe (DoubleLinkedItem m a)) }
  
-- | The 'DoubleLinkedList' type represents an imperative double-linked list.
data DoubleLinkedList m a =  
  DoubleLinkedList { DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead :: Ref m (Maybe (DoubleLinkedItem m a)),
                     DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail :: Ref m (Maybe (DoubleLinkedItem m a)), 
                     DoubleLinkedList m a -> Ref m Int
listSize :: Ref m Int }

-- | Test whether the list is empty.
listNull :: MonadRef m => DoubleLinkedList m a -> Event m Bool
{-# INLINABLE listNull #-}
listNull :: DoubleLinkedList m a -> Event m Bool
listNull DoubleLinkedList m a
x =
  do Maybe (DoubleLinkedItem m a)
head <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) 
     case Maybe (DoubleLinkedItem m a)
head of
       Maybe (DoubleLinkedItem m a)
Nothing -> Bool -> Event m Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
True
       Just DoubleLinkedItem m a
_  -> Bool -> Event m Bool
forall (m :: * -> *) a. Monad m => a -> m a
return Bool
False
    
-- | Return the number of elements in the list.
listCount :: MonadRef m => DoubleLinkedList m a -> Event m Int
{-# INLINABLE listCount #-}
listCount :: DoubleLinkedList m a -> Event m Int
listCount DoubleLinkedList m a
x = Ref m Int -> Event m Int
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x)

-- | Create a new list.
newList :: MonadRef m => Simulation m (DoubleLinkedList m a)
{-# INLINABLE newList #-}
newList :: Simulation m (DoubleLinkedList m a)
newList =
  do Ref m (Maybe (DoubleLinkedItem m a))
head <- Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing 
     Ref m (Maybe (DoubleLinkedItem m a))
tail <- Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
     Ref m Int
size <- Int -> Simulation m (Ref m Int)
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Int
0
     DoubleLinkedList m a -> Simulation m (DoubleLinkedList m a)
forall (m :: * -> *) a. Monad m => a -> m a
return DoubleLinkedList :: forall (m :: * -> *) a.
Ref m (Maybe (DoubleLinkedItem m a))
-> Ref m (Maybe (DoubleLinkedItem m a))
-> Ref m Int
-> DoubleLinkedList m a
DoubleLinkedList { listHead :: Ref m (Maybe (DoubleLinkedItem m a))
listHead = Ref m (Maybe (DoubleLinkedItem m a))
head,
                               listTail :: Ref m (Maybe (DoubleLinkedItem m a))
listTail = Ref m (Maybe (DoubleLinkedItem m a))
tail,
                               listSize :: Ref m Int
listSize = Ref m Int
size }

-- | Insert a new element in the beginning.
listInsertFirst :: MonadRef m => DoubleLinkedList m a -> a -> Event m ()
{-# INLINABLE listInsertFirst #-}
listInsertFirst :: DoubleLinkedList m a -> a -> Event m ()
listInsertFirst DoubleLinkedList m a
x a
v =
  do Int
size <- Ref m Int -> Event m Int
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x)
     Ref m Int -> Int -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x) (Int
size Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
1)
     Maybe (DoubleLinkedItem m a)
head <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x)
     case Maybe (DoubleLinkedItem m a)
head of
       Maybe (DoubleLinkedItem m a)
Nothing ->
         do Ref m (Maybe (DoubleLinkedItem m a))
prev <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
            Ref m (Maybe (DoubleLinkedItem m a))
next <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
            let item :: Maybe (DoubleLinkedItem m a)
item = DoubleLinkedItem m a -> Maybe (DoubleLinkedItem m a)
forall a. a -> Maybe a
Just DoubleLinkedItem :: forall (m :: * -> *) a.
a
-> Ref m (Maybe (DoubleLinkedItem m a))
-> Ref m (Maybe (DoubleLinkedItem m a))
-> DoubleLinkedItem m a
DoubleLinkedItem { itemVal :: a
itemVal = a
v, 
                                               itemPrev :: Ref m (Maybe (DoubleLinkedItem m a))
itemPrev = Ref m (Maybe (DoubleLinkedItem m a))
prev, 
                                               itemNext :: Ref m (Maybe (DoubleLinkedItem m a))
itemNext = Ref m (Maybe (DoubleLinkedItem m a))
next }
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
item
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
item
       Just DoubleLinkedItem m a
h ->
         do Ref m (Maybe (DoubleLinkedItem m a))
prev <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
            Ref m (Maybe (DoubleLinkedItem m a))
next <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
head
            let item :: Maybe (DoubleLinkedItem m a)
item = DoubleLinkedItem m a -> Maybe (DoubleLinkedItem m a)
forall a. a -> Maybe a
Just DoubleLinkedItem :: forall (m :: * -> *) a.
a
-> Ref m (Maybe (DoubleLinkedItem m a))
-> Ref m (Maybe (DoubleLinkedItem m a))
-> DoubleLinkedItem m a
DoubleLinkedItem { itemVal :: a
itemVal = a
v,
                                               itemPrev :: Ref m (Maybe (DoubleLinkedItem m a))
itemPrev = Ref m (Maybe (DoubleLinkedItem m a))
prev,
                                               itemNext :: Ref m (Maybe (DoubleLinkedItem m a))
itemNext = Ref m (Maybe (DoubleLinkedItem m a))
next }
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
h) Maybe (DoubleLinkedItem m a)
item
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
item

-- | Add a new element to the end.
listAddLast :: MonadRef m => DoubleLinkedList m a -> a -> Event m ()
{-# INLINABLE listAddLast #-}
listAddLast :: DoubleLinkedList m a -> a -> Event m ()
listAddLast DoubleLinkedList m a
x a
v =
  do Int
size <- Ref m Int -> Event m Int
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x)
     Ref m Int -> Int -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x) (Int
size Int -> Int -> Int
forall a. Num a => a -> a -> a
+ Int
1)
     Maybe (DoubleLinkedItem m a)
tail <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x)
     case Maybe (DoubleLinkedItem m a)
tail of
       Maybe (DoubleLinkedItem m a)
Nothing ->
         do Ref m (Maybe (DoubleLinkedItem m a))
prev <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
            Ref m (Maybe (DoubleLinkedItem m a))
next <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
            let item :: Maybe (DoubleLinkedItem m a)
item = DoubleLinkedItem m a -> Maybe (DoubleLinkedItem m a)
forall a. a -> Maybe a
Just DoubleLinkedItem :: forall (m :: * -> *) a.
a
-> Ref m (Maybe (DoubleLinkedItem m a))
-> Ref m (Maybe (DoubleLinkedItem m a))
-> DoubleLinkedItem m a
DoubleLinkedItem { itemVal :: a
itemVal = a
v, 
                                               itemPrev :: Ref m (Maybe (DoubleLinkedItem m a))
itemPrev = Ref m (Maybe (DoubleLinkedItem m a))
prev, 
                                               itemNext :: Ref m (Maybe (DoubleLinkedItem m a))
itemNext = Ref m (Maybe (DoubleLinkedItem m a))
next }
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
item
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
item
       Just DoubleLinkedItem m a
t ->
         do Ref m (Maybe (DoubleLinkedItem m a))
prev <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
tail
            Ref m (Maybe (DoubleLinkedItem m a))
next <- Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (t :: (* -> *) -> * -> *) (m :: * -> *) a.
SimulationLift t m =>
Simulation m a -> t m a
liftSimulation (Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
 -> Event m (Ref m (Maybe (DoubleLinkedItem m a))))
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
-> Event m (Ref m (Maybe (DoubleLinkedItem m a)))
forall a b. (a -> b) -> a -> b
$ Maybe (DoubleLinkedItem m a)
-> Simulation m (Ref m (Maybe (DoubleLinkedItem m a)))
forall (m :: * -> *) a. MonadRef m => a -> Simulation m (Ref m a)
newRef Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
            let item :: Maybe (DoubleLinkedItem m a)
item = DoubleLinkedItem m a -> Maybe (DoubleLinkedItem m a)
forall a. a -> Maybe a
Just DoubleLinkedItem :: forall (m :: * -> *) a.
a
-> Ref m (Maybe (DoubleLinkedItem m a))
-> Ref m (Maybe (DoubleLinkedItem m a))
-> DoubleLinkedItem m a
DoubleLinkedItem { itemVal :: a
itemVal = a
v,
                                               itemPrev :: Ref m (Maybe (DoubleLinkedItem m a))
itemPrev = Ref m (Maybe (DoubleLinkedItem m a))
prev,
                                               itemNext :: Ref m (Maybe (DoubleLinkedItem m a))
itemNext = Ref m (Maybe (DoubleLinkedItem m a))
next }
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
t) Maybe (DoubleLinkedItem m a)
item
            Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
item

-- | Remove the first element.
listRemoveFirst :: MonadRef m => DoubleLinkedList m a -> Event m ()
{-# INLINABLE listRemoveFirst #-}
listRemoveFirst :: DoubleLinkedList m a -> Event m ()
listRemoveFirst DoubleLinkedList m a
x =
  do Maybe (DoubleLinkedItem m a)
head <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) 
     case Maybe (DoubleLinkedItem m a)
head of
       Maybe (DoubleLinkedItem m a)
Nothing ->
         [Char] -> Event m ()
forall a. HasCallStack => [Char] -> a
error [Char]
"Empty list: listRemoveFirst"
       Just DoubleLinkedItem m a
h ->
         do Int
size <- Ref m Int -> Event m Int
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x)
            Ref m Int -> Int -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x) (Int
size Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1)
            Maybe (DoubleLinkedItem m a)
head' <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
h)
            case Maybe (DoubleLinkedItem m a)
head' of
              Maybe (DoubleLinkedItem m a)
Nothing ->
                do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                   Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
              Just DoubleLinkedItem m a
h' ->
                do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
h') Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                   Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
head'

-- | Remove the last element.
listRemoveLast :: MonadRef m => DoubleLinkedList m a -> Event m ()
{-# INLINABLE listRemoveLast #-}
listRemoveLast :: DoubleLinkedList m a -> Event m ()
listRemoveLast DoubleLinkedList m a
x =
  do Maybe (DoubleLinkedItem m a)
tail <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) 
     case Maybe (DoubleLinkedItem m a)
tail of
       Maybe (DoubleLinkedItem m a)
Nothing ->
         [Char] -> Event m ()
forall a. HasCallStack => [Char] -> a
error [Char]
"Empty list: listRemoveLast"
       Just DoubleLinkedItem m a
t ->
         do Int
size <- Ref m Int -> Event m Int
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x)
            Ref m Int -> Int -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x) (Int
size Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1)
            Maybe (DoubleLinkedItem m a)
tail' <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
t)
            case Maybe (DoubleLinkedItem m a)
tail' of
              Maybe (DoubleLinkedItem m a)
Nothing ->
                do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                   Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
              Just DoubleLinkedItem m a
t' ->
                do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
t') Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                   Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
tail'

-- | Return the first element.
listFirst :: MonadRef m => DoubleLinkedList m a -> Event m a
{-# INLINABLE listFirst #-}
listFirst :: DoubleLinkedList m a -> Event m a
listFirst DoubleLinkedList m a
x =
  do Maybe (DoubleLinkedItem m a)
head <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x)
     case Maybe (DoubleLinkedItem m a)
head of
       Maybe (DoubleLinkedItem m a)
Nothing ->
         [Char] -> Event m a
forall a. HasCallStack => [Char] -> a
error [Char]
"Empty list: listFirst"
       Just DoubleLinkedItem m a
h ->
         a -> Event m a
forall (m :: * -> *) a. Monad m => a -> m a
return (a -> Event m a) -> a -> Event m a
forall a b. (a -> b) -> a -> b
$ DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
h

-- | Return the last element.
listLast :: MonadRef m => DoubleLinkedList m a -> Event m a
{-# INLINABLE listLast #-}
listLast :: DoubleLinkedList m a -> Event m a
listLast DoubleLinkedList m a
x =
  do Maybe (DoubleLinkedItem m a)
tail <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x)
     case Maybe (DoubleLinkedItem m a)
tail of
       Maybe (DoubleLinkedItem m a)
Nothing ->
         [Char] -> Event m a
forall a. HasCallStack => [Char] -> a
error [Char]
"Empty list: listLast"
       Just DoubleLinkedItem m a
t ->
         a -> Event m a
forall (m :: * -> *) a. Monad m => a -> m a
return (a -> Event m a) -> a -> Event m a
forall a b. (a -> b) -> a -> b
$ DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
t

-- | Remove the specified element from the list and return a flag
-- indicating whether the element was found and removed.
listRemove :: (Eq a, Functor m, MonadRef m) => DoubleLinkedList m a -> a -> Event m Bool
{-# INLINABLE listRemove #-}
listRemove :: DoubleLinkedList m a -> a -> Event m Bool
listRemove DoubleLinkedList m a
x a
v = (Maybe a -> Bool) -> Event m (Maybe a) -> Event m Bool
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Maybe a -> Bool
forall a. Maybe a -> Bool
isJust (Event m (Maybe a) -> Event m Bool)
-> Event m (Maybe a) -> Event m Bool
forall a b. (a -> b) -> a -> b
$ DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
forall (m :: * -> *) a.
MonadRef m =>
DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
listRemoveBy DoubleLinkedList m a
x (a -> a -> Bool
forall a. Eq a => a -> a -> Bool
== a
v)

-- | Remove an element satisfying the specified predicate and return
-- the element if found.
listRemoveBy :: MonadRef m => DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
{-# INLINABLE listRemoveBy #-}
listRemoveBy :: DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
listRemoveBy DoubleLinkedList m a
x a -> Bool
p = Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Event m (Maybe (DoubleLinkedItem m a))
-> (Maybe (DoubleLinkedItem m a) -> Event m (Maybe a))
-> Event m (Maybe a)
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
loop
  where loop :: Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
loop Maybe (DoubleLinkedItem m a)
item =
          case Maybe (DoubleLinkedItem m a)
item of
            Maybe (DoubleLinkedItem m a)
Nothing   -> Maybe a -> Event m (Maybe a)
forall (m :: * -> *) a. Monad m => a -> m a
return Maybe a
forall a. Maybe a
Nothing
            Just DoubleLinkedItem m a
item ->
              do let f :: Bool
f = a -> Bool
p (DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
item)
                 if Bool -> Bool
not Bool
f
                   then Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
item) Event m (Maybe (DoubleLinkedItem m a))
-> (Maybe (DoubleLinkedItem m a) -> Event m (Maybe a))
-> Event m (Maybe a)
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
loop
                   else do Int
size <- Ref m Int -> Event m Int
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x)
                           Maybe (DoubleLinkedItem m a)
prev <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
item)
                           Maybe (DoubleLinkedItem m a)
next <- Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
item)
                           Ref m Int -> Int -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
x) (Int
size Int -> Int -> Int
forall a. Num a => a -> a -> a
- Int
1)
                           case (Maybe (DoubleLinkedItem m a)
prev, Maybe (DoubleLinkedItem m a)
next) of
                             (Maybe (DoubleLinkedItem m a)
Nothing, Maybe (DoubleLinkedItem m a)
Nothing) ->
                               do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                                  Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                             (Maybe (DoubleLinkedItem m a)
Nothing, head' :: Maybe (DoubleLinkedItem m a)
head'@(Just DoubleLinkedItem m a
item')) ->
                               do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
item') Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                                  Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
head'
                             (tail' :: Maybe (DoubleLinkedItem m a)
tail'@(Just DoubleLinkedItem m a
item'), Maybe (DoubleLinkedItem m a)
Nothing) ->
                               do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
item') Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
                                  Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Maybe (DoubleLinkedItem m a)
tail'
                             (Just DoubleLinkedItem m a
prev', Just DoubleLinkedItem m a
next') ->
                               do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
prev') (DoubleLinkedItem m a -> Maybe (DoubleLinkedItem m a)
forall a. a -> Maybe a
Just DoubleLinkedItem m a
next')
                                  Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
next') (DoubleLinkedItem m a -> Maybe (DoubleLinkedItem m a)
forall a. a -> Maybe a
Just DoubleLinkedItem m a
prev')
                           Maybe a -> Event m (Maybe a)
forall (m :: * -> *) a. Monad m => a -> m a
return (a -> Maybe a
forall a. a -> Maybe a
Just (a -> Maybe a) -> a -> Maybe a
forall a b. (a -> b) -> a -> b
$ DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
item)

-- | Detect whether the specified element is contained in the list.
listContains :: (Eq a, Functor m, MonadRef m) => DoubleLinkedList m a -> a -> Event m Bool
{-# INLINABLE listContains #-}
listContains :: DoubleLinkedList m a -> a -> Event m Bool
listContains DoubleLinkedList m a
x a
v = (Maybe a -> Bool) -> Event m (Maybe a) -> Event m Bool
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap Maybe a -> Bool
forall a. Maybe a -> Bool
isJust (Event m (Maybe a) -> Event m Bool)
-> Event m (Maybe a) -> Event m Bool
forall a b. (a -> b) -> a -> b
$ DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
forall (m :: * -> *) a.
MonadRef m =>
DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
listContainsBy DoubleLinkedList m a
x (a -> a -> Bool
forall a. Eq a => a -> a -> Bool
== a
v)

-- | Detect whether an element satisfying the specified predicate is contained in the list.
listContainsBy :: MonadRef m => DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
{-# INLINABLE listContainsBy #-}
listContainsBy :: DoubleLinkedList m a -> (a -> Bool) -> Event m (Maybe a)
listContainsBy DoubleLinkedList m a
x a -> Bool
p = Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
x) Event m (Maybe (DoubleLinkedItem m a))
-> (Maybe (DoubleLinkedItem m a) -> Event m (Maybe a))
-> Event m (Maybe a)
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
forall (m :: * -> *).
MonadRef m =>
Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
loop
  where loop :: Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
loop Maybe (DoubleLinkedItem m a)
item =
          case Maybe (DoubleLinkedItem m a)
item of
            Maybe (DoubleLinkedItem m a)
Nothing   -> Maybe a -> Event m (Maybe a)
forall (m :: * -> *) a. Monad m => a -> m a
return Maybe a
forall a. Maybe a
Nothing
            Just DoubleLinkedItem m a
item ->
              do let f :: Bool
f = a -> Bool
p (DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
item)
                 if Bool -> Bool
not Bool
f
                   then Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemNext DoubleLinkedItem m a
item) Event m (Maybe (DoubleLinkedItem m a))
-> (Maybe (DoubleLinkedItem m a) -> Event m (Maybe a))
-> Event m (Maybe a)
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= Maybe (DoubleLinkedItem m a) -> Event m (Maybe a)
loop
                   else Maybe a -> Event m (Maybe a)
forall (m :: * -> *) a. Monad m => a -> m a
return (Maybe a -> Event m (Maybe a)) -> Maybe a -> Event m (Maybe a)
forall a b. (a -> b) -> a -> b
$ a -> Maybe a
forall a. a -> Maybe a
Just (DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
item)

-- | Clear the contents of the list.
clearList :: MonadRef m => DoubleLinkedList m a -> Event m ()
{-# INLINABLE clearList #-}
clearList :: DoubleLinkedList m a -> Event m ()
clearList DoubleLinkedList m a
q =
  do Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listHead DoubleLinkedList m a
q) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
     Ref m (Maybe (DoubleLinkedItem m a))
-> Maybe (DoubleLinkedItem m a) -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
q) Maybe (DoubleLinkedItem m a)
forall a. Maybe a
Nothing
     Ref m Int -> Int -> Event m ()
forall (m :: * -> *) a. MonadRef m => Ref m a -> a -> Event m ()
writeRef (DoubleLinkedList m a -> Ref m Int
forall (m :: * -> *) a. DoubleLinkedList m a -> Ref m Int
listSize DoubleLinkedList m a
q) Int
0

-- | Freeze the list and return its contents.
freezeList :: MonadRef m => DoubleLinkedList m a -> Event m [a]
{-# INLINABLE freezeList #-}
freezeList :: DoubleLinkedList m a -> Event m [a]
freezeList DoubleLinkedList m a
x = Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedList m a -> Ref m (Maybe (DoubleLinkedItem m a))
listTail DoubleLinkedList m a
x) Event m (Maybe (DoubleLinkedItem m a))
-> (Maybe (DoubleLinkedItem m a) -> Event m [a]) -> Event m [a]
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= [a] -> Maybe (DoubleLinkedItem m a) -> Event m [a]
forall (m :: * -> *) a.
MonadRef m =>
[a] -> Maybe (DoubleLinkedItem m a) -> Event m [a]
loop []
  where loop :: [a] -> Maybe (DoubleLinkedItem m a) -> Event m [a]
loop [a]
acc Maybe (DoubleLinkedItem m a)
Nothing     = [a] -> Event m [a]
forall (m :: * -> *) a. Monad m => a -> m a
return [a]
acc
        loop [a]
acc (Just DoubleLinkedItem m a
item) = Ref m (Maybe (DoubleLinkedItem m a))
-> Event m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a. MonadRef m => Ref m a -> Event m a
readRef (DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
forall (m :: * -> *) a.
DoubleLinkedItem m a -> Ref m (Maybe (DoubleLinkedItem m a))
itemPrev DoubleLinkedItem m a
item) Event m (Maybe (DoubleLinkedItem m a))
-> (Maybe (DoubleLinkedItem m a) -> Event m [a]) -> Event m [a]
forall (m :: * -> *) a b. Monad m => m a -> (a -> m b) -> m b
>>= [a] -> Maybe (DoubleLinkedItem m a) -> Event m [a]
loop (DoubleLinkedItem m a -> a
forall (m :: * -> *) a. DoubleLinkedItem m a -> a
itemVal DoubleLinkedItem m a
item a -> [a] -> [a]
forall a. a -> [a] -> [a]
: [a]
acc)