{-# LANGUAGE DerivingStrategies    #-}
{-# LANGUAGE FlexibleContexts      #-}
{-# LANGUAGE MultiParamTypeClasses #-}
{-# LANGUAGE NoImplicitPrelude     #-}
{-# LANGUAGE TemplateHaskell       #-}
{-# LANGUAGE ViewPatterns          #-}

module PlutusTx.Data.AssocMap (
  Map,
  lookup,
  member,
  insert,
  delete,
  singleton,
  empty,
  null,
  toList,
  toBuiltinList,
  safeFromList,
  unsafeFromList,
  unsafeFromBuiltinList,
  noDuplicateKeys,
  all,
  any,
  union,
  unionWith,
  keys,
  map,
  mapThese,
  foldr,
  ) where

import PlutusTx.Builtins qualified as P
import PlutusTx.Builtins.Internal qualified as BI
import PlutusTx.IsData qualified as P
import PlutusTx.Lift (makeLift)
import PlutusTx.List qualified as List
import PlutusTx.Prelude hiding (all, any, foldr, map, null, toList, uncons)
import PlutusTx.Prelude qualified
import PlutusTx.These


import Prelude qualified as Haskell

{- | A map associating keys and values backed by `P.BuiltinData`.

This implementation has the following characteristics:

  * The `P.toBuiltinData` and `P.unsafeFromBuiltinData` operations are no-op.
  * Other operations are slower than @PlutusTx.AssocMap.Map@, although equality
    checks on keys can be faster due to `P.equalsData`.
  * Many operations involve converting the keys and\/or values to\/from `P.BuiltinData`.

Therefore this implementation is likely a better choice than "PlutusTx.AssocMap.Map"
if it is part of a data type defined using @asData@, and the key and value types
have efficient `P.toBuiltinData` and `P.unsafeFromBuiltinData` operations (e.g., they
are primitive types or types defined using @asData@).

A `Map` is considered well-defined if it has no duplicate keys. Most operations
preserve the definedness of the resulting `Map` unless otherwise noted.
It is important to observe that, in comparison to standard map implementations,
this implementation provides slow lookup and update operations because it is based
on a list representation.
-}
newtype Map k a = Map (BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData))
  deriving stock (Int -> Map k a -> ShowS
[Map k a] -> ShowS
Map k a -> String
(Int -> Map k a -> ShowS)
-> (Map k a -> String) -> ([Map k a] -> ShowS) -> Show (Map k a)
forall a.
(Int -> a -> ShowS) -> (a -> String) -> ([a] -> ShowS) -> Show a
forall k a. Int -> Map k a -> ShowS
forall k a. [Map k a] -> ShowS
forall k a. Map k a -> String
$cshowsPrec :: forall k a. Int -> Map k a -> ShowS
showsPrec :: Int -> Map k a -> ShowS
$cshow :: forall k a. Map k a -> String
show :: Map k a -> String
$cshowList :: forall k a. [Map k a] -> ShowS
showList :: [Map k a] -> ShowS
Haskell.Show)

instance P.ToData (Map k a) where
  {-# INLINEABLE toBuiltinData #-}
  toBuiltinData :: Map k a -> BuiltinData
toBuiltinData (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
d) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> BuiltinData
BI.mkMap BuiltinList (BuiltinPair BuiltinData BuiltinData)
d

instance P.FromData (Map k a) where
  {-# INLINABLE fromBuiltinData #-}
  fromBuiltinData :: BuiltinData -> Maybe (Map k a)
fromBuiltinData = Map k a -> Maybe (Map k a)
forall a. a -> Maybe a
Just (Map k a -> Maybe (Map k a))
-> (BuiltinData -> Map k a) -> BuiltinData -> Maybe (Map k a)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> (BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinData
-> Map k a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. BuiltinData -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
BI.unsafeDataAsMap

instance P.UnsafeFromData (Map k a) where
  {-# INLINABLE unsafeFromBuiltinData #-}
  unsafeFromBuiltinData :: BuiltinData -> Map k a
unsafeFromBuiltinData = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> (BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinData
-> Map k a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. BuiltinData -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
BI.unsafeDataAsMap

{-# INLINEABLE lookup #-}
-- | Look up the value corresponding to the key.
-- If the `Map` is not well-defined, the result is the value associated with
-- the left-most occurrence of the key in the list.
-- This operation is O(n).
lookup :: forall k a. (P.ToData k, P.UnsafeFromData a) => k -> Map k a -> Maybe a
lookup :: forall k a. (ToData k, UnsafeFromData a) => k -> Map k a -> Maybe a
lookup (k -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
k) (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData (BuiltinData -> a) -> Maybe BuiltinData -> Maybe a
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Maybe BuiltinData
lookup' BuiltinData
k BuiltinList (BuiltinPair BuiltinData BuiltinData)
m

lookup'
  :: BuiltinData
  -> BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
  -> Maybe BuiltinData
lookup' :: BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Maybe BuiltinData
lookup' BuiltinData
k BuiltinList (BuiltinPair BuiltinData BuiltinData)
m = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Maybe BuiltinData
forall {a}. BuiltinList (BuiltinPair BuiltinData a) -> Maybe a
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
  where
    go :: BuiltinList (BuiltinPair BuiltinData a) -> Maybe a
go BuiltinList (BuiltinPair BuiltinData a)
xs =
      BuiltinList (BuiltinPair BuiltinData a)
-> (() -> Maybe a)
-> (BuiltinPair BuiltinData a
    -> BuiltinList (BuiltinPair BuiltinData a) -> Maybe a)
-> Maybe a
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData a)
xs
        (\() -> Maybe a
forall a. Maybe a
Nothing)
        ( \BuiltinPair BuiltinData a
hd ->
            let k' :: BuiltinData
k' = BuiltinPair BuiltinData a -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData a
hd
             in if BuiltinData -> BuiltinData -> Bool
P.equalsData BuiltinData
k BuiltinData
k'
                  then \BuiltinList (BuiltinPair BuiltinData a)
_ -> a -> Maybe a
forall a. a -> Maybe a
Just (BuiltinPair BuiltinData a -> a
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData a
hd)
                  else BuiltinList (BuiltinPair BuiltinData a) -> Maybe a
go
        )

{-# INLINEABLE member #-}
-- | Check if the key is in the `Map`.
member :: forall k a. (P.ToData k) => k -> Map k a -> Bool
member :: forall k a. ToData k => k -> Map k a -> Bool
member (k -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
k) (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
member' BuiltinData
k BuiltinList (BuiltinPair BuiltinData BuiltinData)
m

member' :: BuiltinData -> BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) -> Bool
member' :: BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
member' BuiltinData
k = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go
  where
    go :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) -> Bool
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> Bool)
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool)
-> Bool
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> Bool
False)
        ( \BuiltinPair BuiltinData BuiltinData
hd ->
            let k' :: BuiltinData
k' = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
             in if BuiltinData -> BuiltinData -> Bool
P.equalsData BuiltinData
k BuiltinData
k'
                  then \BuiltinList (BuiltinPair BuiltinData BuiltinData)
_ -> Bool
True
                  else BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go
        )

{-# INLINEABLE insert #-}
-- | Insert a key-value pair into the `Map`. If the key is already present,
-- the value is updated.
insert :: forall k a. (P.ToData k, P.ToData a) => k -> a -> Map k a -> Map k a
insert :: forall k a. (ToData k, ToData a) => k -> a -> Map k a -> Map k a
insert (k -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
k) (a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
a) (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall a b. (a -> b) -> a -> b
$ BuiltinData
-> BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
insert' BuiltinData
k BuiltinData
a BuiltinList (BuiltinPair BuiltinData BuiltinData)
m

insert'
  :: BuiltinData
  -> BuiltinData
  -> BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
  -> BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
insert' :: BuiltinData
-> BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
insert' BuiltinData
k BuiltinData
a = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go
  where
    go ::
      BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) ->
      BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k BuiltinData
a) BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k' :: BuiltinData
k' = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
             in if BuiltinData -> BuiltinData -> Bool
P.equalsData BuiltinData
k BuiltinData
k'
                  then BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k BuiltinData
a) BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl
                  else BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons BuiltinPair BuiltinData BuiltinData
hd (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl)
        )

{-# INLINEABLE delete #-}
-- | Delete a key value pair from the `Map`.
-- If the `Map` is not well-defined, it deletes the pair associated with the
-- left-most occurrence of the key in the list.
delete :: forall k a. (P.ToData k) => k -> Map k a -> Map k a
delete :: forall k a. ToData k => k -> Map k a -> Map k a
delete (k -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
k) (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall a b. (a -> b) -> a -> b
$ BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
delete' BuiltinData
k BuiltinList (BuiltinPair BuiltinData BuiltinData)
m

delete' ::
  BuiltinData ->
  BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) ->
  BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
delete' :: BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
delete' BuiltinData
k = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go
  where
    go ::
      BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) ->
      BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k' :: BuiltinData
k' = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
             in if BuiltinData -> BuiltinData -> Bool
P.equalsData BuiltinData
k BuiltinData
k'
                  then BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl
                  else BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons BuiltinPair BuiltinData BuiltinData
hd (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl)
        )

{-# INLINEABLE singleton #-}
-- | Create an `Map` with a single key-value pair.
singleton :: forall k a. (P.ToData k, P.ToData a) => k -> a -> Map k a
singleton :: forall k a. (ToData k, ToData a) => k -> a -> Map k a
singleton (k -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
k) (a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData -> BuiltinData
a) =
  BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall a b. (a -> b) -> a -> b
$ BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k BuiltinData
a) BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil

{-# INLINEABLE empty #-}
-- | An empty `Map`.
empty :: forall k a. Map k a
empty :: forall k a. Map k a
empty = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil

{-# INLINEABLE null #-}
-- | Check if the `Map` is empty.
null :: forall k a. Map k a -> Bool
null :: forall k a. Map k a -> Bool
null (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
forall a. BuiltinList a -> Bool
P.null BuiltinList (BuiltinPair BuiltinData BuiltinData)
m

{-# INLINEABLE safeFromList #-}
-- | Create an `Map` from a list of key-value pairs.
-- In case of duplicates, this function will keep only one entry (the one that precedes).
-- In other words, this function de-duplicates the input list.
safeFromList :: forall k a . (P.ToData k, P.ToData a) => [(k, a)] -> Map k a
safeFromList :: forall k a. (ToData k, ToData a) => [(k, a)] -> Map k a
safeFromList =
  BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map
    (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> ([(k, a)] -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> [(k, a)]
-> Map k a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [(BuiltinData, BuiltinData)]
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a arep. HasToOpaque a arep => a -> arep
toOpaque
    ([(BuiltinData, BuiltinData)]
 -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> ([(k, a)] -> [(BuiltinData, BuiltinData)])
-> [(k, a)]
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ((k, a)
 -> [(BuiltinData, BuiltinData)] -> [(BuiltinData, BuiltinData)])
-> [(BuiltinData, BuiltinData)]
-> [(k, a)]
-> [(BuiltinData, BuiltinData)]
forall a b. (a -> b -> b) -> b -> [a] -> b
List.foldr ((k
 -> a
 -> [(BuiltinData, BuiltinData)]
 -> [(BuiltinData, BuiltinData)])
-> (k, a)
-> [(BuiltinData, BuiltinData)]
-> [(BuiltinData, BuiltinData)]
forall a b c. (a -> b -> c) -> (a, b) -> c
uncurry k
-> a
-> [(BuiltinData, BuiltinData)]
-> [(BuiltinData, BuiltinData)]
forall {t} {t} {a}.
(ToData t, ToData t, ToData a) =>
t -> t -> [(BuiltinData, a)] -> [(BuiltinData, BuiltinData)]
go) []
  where
    go :: t -> t -> [(BuiltinData, a)] -> [(BuiltinData, BuiltinData)]
go t
k t
v [] = [(t -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData t
k, t -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData t
v)]
    go t
k t
v ((BuiltinData
k', a
v') : [(BuiltinData, a)]
rest) =
      if t -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData t
k BuiltinData -> BuiltinData -> Bool
forall a. Eq a => a -> a -> Bool
== BuiltinData
k'
        then (t -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData t
k, t -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData t
v) (BuiltinData, BuiltinData)
-> [(BuiltinData, BuiltinData)] -> [(BuiltinData, BuiltinData)]
forall a. a -> [a] -> [a]
: t -> t -> [(BuiltinData, a)] -> [(BuiltinData, BuiltinData)]
go t
k t
v [(BuiltinData, a)]
rest
        else (BuiltinData -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData BuiltinData
k', a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData a
v') (BuiltinData, BuiltinData)
-> [(BuiltinData, BuiltinData)] -> [(BuiltinData, BuiltinData)]
forall a. a -> [a] -> [a]
: t -> t -> [(BuiltinData, a)] -> [(BuiltinData, BuiltinData)]
go t
k t
v [(BuiltinData, a)]
rest

{-# INLINEABLE unsafeFromList #-}
-- | Unsafely create an 'Map' from a list of pairs.
-- This should _only_ be applied to lists which have been checked to not
-- contain duplicate keys, otherwise the resulting 'Map' will contain
-- conflicting entries (two entries sharing the same key), and therefore be ill-defined.
unsafeFromList :: (P.ToData k, P.ToData a) => [(k, a)] -> Map k a
unsafeFromList :: forall k a. (ToData k, ToData a) => [(k, a)] -> Map k a
unsafeFromList =
  BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map
    (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a)
-> ([(k, a)] -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> [(k, a)]
-> Map k a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. [(BuiltinData, BuiltinData)]
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a arep. HasToOpaque a arep => a -> arep
toOpaque
    ([(BuiltinData, BuiltinData)]
 -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> ([(k, a)] -> [(BuiltinData, BuiltinData)])
-> [(k, a)]
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall b c a. (b -> c) -> (a -> b) -> a -> c
. ((k, a) -> (BuiltinData, BuiltinData))
-> [(k, a)] -> [(BuiltinData, BuiltinData)]
forall a b. (a -> b) -> [a] -> [b]
PlutusTx.Prelude.map (\(k
k, a
a) -> (k -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData k
k, a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData a
a))

{-# INLINEABLE noDuplicateKeys #-}
-- | Check if the `Map` is well-defined. Warning: this operation is O(n^2).
noDuplicateKeys :: forall k a. Map k a -> Bool
noDuplicateKeys :: forall k a. Map k a -> Bool
noDuplicateKeys (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
  where
    go :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) -> Bool
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> Bool)
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool)
-> Bool
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> Bool
True)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
             in if BuiltinData -> Map BuiltinData Any -> Bool
forall k a. ToData k => k -> Map k a -> Bool
member BuiltinData
k (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Map BuiltinData Any
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl) then Bool
False else BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl
        )

{-# INLINEABLE all #-}
--- | Check if all values in the `Map` satisfy the predicate.
all :: forall k a. (P.UnsafeFromData a) => (a -> Bool) -> Map k a -> Bool
all :: forall k a. UnsafeFromData a => (a -> Bool) -> Map k a -> Bool
all a -> Bool
p (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
  where
    go :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) -> Bool
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> Bool)
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool)
-> Bool
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> Bool
True)
        ( \BuiltinPair BuiltinData BuiltinData
hd ->
            let a :: a
a = BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData (BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd)
             in if a -> Bool
p a
a then BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go else \BuiltinList (BuiltinPair BuiltinData BuiltinData)
_ -> Bool
False
        )

{-# INLINEABLE any #-}
-- | Check if any value in the `Map` satisfies the predicate.
any :: forall k a. (P.UnsafeFromData a) => (a -> Bool) -> Map k a -> Bool
any :: forall k a. UnsafeFromData a => (a -> Bool) -> Map k a -> Bool
any a -> Bool
p (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
  where
    go :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) -> Bool
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> Bool)
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool)
-> Bool
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> Bool
False)
        ( \BuiltinPair BuiltinData BuiltinData
hd ->
            let a :: a
a = BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData (BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd)
             in if a -> Bool
p a
a then \BuiltinList (BuiltinPair BuiltinData BuiltinData)
_ -> Bool
True else BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
go
        )

{-# INLINEABLE union #-}

-- | Combine two 'Map's into one. It saves both values if the key is present in both maps.
union ::
  forall k a b.
  (P.UnsafeFromData a, P.UnsafeFromData b, P.ToData a, P.ToData b) =>
  Map k a ->
  Map k b ->
  Map k (These a b)
union :: forall k a b.
(UnsafeFromData a, UnsafeFromData b, ToData a, ToData b) =>
Map k a -> Map k b -> Map k (These a b)
union (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls) (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs) = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Map k (These a b)
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
res
  where
    goLeft :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
goLeft BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                v :: BuiltinData
v = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd
                v' :: BuiltinData
v' = case BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Maybe BuiltinData
lookup' BuiltinData
k BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs of
                  Just BuiltinData
r ->
                    These a b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData
                      ( a -> b -> These a b
forall a b. a -> b -> These a b
These
                          (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v)
                          (BuiltinData -> b
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
r)
                        :: These a b
                      )
                  Maybe BuiltinData
Nothing ->
                    These a b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData (a -> These a b
forall a b. a -> These a b
This (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v) :: These a b)
             in BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k BuiltinData
v') (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
goLeft BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl)
        )

    goRight :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
goRight BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                v :: BuiltinData
v = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd
                v' :: BuiltinData
v' = case BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Maybe BuiltinData
lookup' BuiltinData
k BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls of
                  Just BuiltinData
r ->
                    These a b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData
                      ( a -> b -> These a b
forall a b. a -> b -> These a b
These
                          (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v)
                          (BuiltinData -> b
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
r)
                        :: These a b
                      )
                  Maybe BuiltinData
Nothing ->
                    These a b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData (b -> These a b
forall a b. b -> These a b
That (BuiltinData -> b
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v) :: These a b)
             in BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k BuiltinData
v') (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
goRight BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl)
        )

    res :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
res = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
goLeft BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
`safeAppend` BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
goRight BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs

    safeAppend :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
safeAppend BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs1 BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs2 =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs1
        (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs2)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                v :: BuiltinData
v = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd
             in BuiltinData
-> BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
insert' BuiltinData
k BuiltinData
v (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
safeAppend BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs2)
        )

{-# INLINEABLE unionWith #-}
-- | Combine two 'Map's with the given combination function.
unionWith ::
  forall k a.
  (P.UnsafeFromData a, P.ToData a) =>
  (a -> a -> a) ->
  Map k a ->
  Map k a ->
  Map k a
unionWith :: forall k a.
(UnsafeFromData a, ToData a) =>
(a -> a -> a) -> Map k a -> Map k a -> Map k a
unionWith a -> a -> a
f (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls) (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs) =
  BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
res
  where
    ls' :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
    ls' :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls' = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls
      where
        go :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
          BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
            BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
            (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
            ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
                let k' :: BuiltinData
k' = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                    v' :: BuiltinData
v' = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd
                    v'' :: BuiltinData
v'' = case BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> Maybe BuiltinData
lookup' BuiltinData
k' BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs of
                      Just BuiltinData
r ->
                        a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData
                          (a -> a -> a
f (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v') (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
r))
                      Maybe BuiltinData
Nothing -> BuiltinData
v'
                 in BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k' BuiltinData
v'') (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl)
            )

    rs' :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
    rs' :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs' = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs
      where
        go :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
          BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
            BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
            (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
            ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
                let k' :: BuiltinData
k' = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                    tl' :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl' = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl
                 in if BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Bool
member' BuiltinData
k' BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls
                      then BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl'
                      else BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl'
            )

    res :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
    res :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
res = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall {a}. BuiltinList a -> BuiltinList a -> BuiltinList a
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs' BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls'
      where
        go :: BuiltinList a -> BuiltinList a -> BuiltinList a
go BuiltinList a
acc BuiltinList a
xs =
          BuiltinList a
-> (() -> BuiltinList a)
-> (a -> BuiltinList a -> BuiltinList a)
-> BuiltinList a
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
            BuiltinList a
xs
            (\() -> BuiltinList a
acc)
            (\a
hd -> BuiltinList a -> BuiltinList a -> BuiltinList a
go (a -> BuiltinList a -> BuiltinList a
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons a
hd BuiltinList a
acc))

{-# INLINEABLE toList #-}
-- | Convert the `Map` to a list of key-value pairs. This operation is O(n).
-- See 'toBuiltinList' for a more efficient alternative.
toList :: (P.UnsafeFromData k, P.UnsafeFromData a) => Map k a -> [(k, a)]
toList :: forall k a.
(UnsafeFromData k, UnsafeFromData a) =>
Map k a -> [(k, a)]
toList Map k a
d = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> [(k, a)]
forall {a} {b}.
(UnsafeFromData a, UnsafeFromData b) =>
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> [(a, b)]
go (Map k a -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall k a.
Map k a -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
toBuiltinList Map k a
d)
  where
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData) -> [(a, b)]
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> [(a, b)])
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> [(a, b)])
-> [(a, b)]
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> [])
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData (BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd), BuiltinData -> b
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData (BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd))
              (a, b) -> [(a, b)] -> [(a, b)]
forall a. a -> [a] -> [a]
: BuiltinList (BuiltinPair BuiltinData BuiltinData) -> [(a, b)]
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl
        )

{-# INLINEABLE toBuiltinList #-}
-- | Convert the `Map` to a `P.BuiltinList` of key-value pairs. This operation is O(1).
toBuiltinList :: Map k a -> BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
toBuiltinList :: forall k a.
Map k a -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
toBuiltinList (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
d) = BuiltinList (BuiltinPair BuiltinData BuiltinData)
d

{-# INLINEABLE unsafeFromBuiltinList #-}
-- | Unsafely create an 'Map' from a `P.BuiltinList` of key-value pairs.
-- This function is unsafe because it assumes that the elements of the list can be safely
-- decoded from their 'BuiltinData' representation.
unsafeFromBuiltinList ::
  forall k a.
  BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData) ->
  Map k a
unsafeFromBuiltinList :: forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
unsafeFromBuiltinList = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map

{-# INLINEABLE nil #-}
-- | An empty `P.BuiltinList` of key-value pairs.
nil :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
nil :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil = BuiltinUnit -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
BI.mkNilPairData BuiltinUnit
BI.unitval

keys'
  :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
  -> BI.BuiltinList BuiltinData
keys' :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList BuiltinData
keys' = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList BuiltinData
forall {b}.
BuiltinList (BuiltinPair BuiltinData b) -> BuiltinList BuiltinData
go
  where
    go :: BuiltinList (BuiltinPair BuiltinData b) -> BuiltinList BuiltinData
go BuiltinList (BuiltinPair BuiltinData b)
xs =
      BuiltinList (BuiltinPair BuiltinData b)
-> (() -> BuiltinList BuiltinData)
-> (BuiltinPair BuiltinData b
    -> BuiltinList (BuiltinPair BuiltinData b)
    -> BuiltinList BuiltinData)
-> BuiltinList BuiltinData
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData b)
xs
        (\() -> BuiltinUnit -> BuiltinList BuiltinData
BI.mkNilData BuiltinUnit
BI.unitval)
        ( \BuiltinPair BuiltinData b
hd BuiltinList (BuiltinPair BuiltinData b)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData b -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData b
hd
             in BuiltinData -> BuiltinList BuiltinData -> BuiltinList BuiltinData
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons BuiltinData
k (BuiltinList (BuiltinPair BuiltinData b) -> BuiltinList BuiltinData
go BuiltinList (BuiltinPair BuiltinData b)
tl)
        )

{-# INLINEABLE keys #-}
keys :: forall k a. Map k a -> BI.BuiltinList BuiltinData
keys :: forall k a. Map k a -> BuiltinList BuiltinData
keys (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList BuiltinData
keys' BuiltinList (BuiltinPair BuiltinData BuiltinData)
m

{-# INLINEABLE mapThese #-}
mapThese
  :: forall v k a b
  . ( P.ToData a, P.ToData b, P.UnsafeFromData v)
  => (v -> These a b) -> Map k v -> (Map k a, Map k b)
mapThese :: forall v k a b.
(ToData a, ToData b, UnsafeFromData v) =>
(v -> These a b) -> Map k v -> (Map k a, Map k b)
mapThese v -> These a b
f (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls, BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k b
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs)
  where
    (BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls, BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs) = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (BuiltinList (BuiltinPair BuiltinData BuiltinData),
    BuiltinList (BuiltinPair BuiltinData BuiltinData))
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
    go
      :: BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
      ->
        ( BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
        , BI.BuiltinList (BI.BuiltinPair BuiltinData BuiltinData)
        )
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (BuiltinList (BuiltinPair BuiltinData BuiltinData),
    BuiltinList (BuiltinPair BuiltinData BuiltinData))
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (()
    -> (BuiltinList (BuiltinPair BuiltinData BuiltinData),
        BuiltinList (BuiltinPair BuiltinData BuiltinData)))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> (BuiltinList (BuiltinPair BuiltinData BuiltinData),
        BuiltinList (BuiltinPair BuiltinData BuiltinData)))
-> (BuiltinList (BuiltinPair BuiltinData BuiltinData),
    BuiltinList (BuiltinPair BuiltinData BuiltinData))
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> (BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil, BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil))
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                v :: BuiltinData
v = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd
                (BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls', BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs') = BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (BuiltinList (BuiltinPair BuiltinData BuiltinData),
    BuiltinList (BuiltinPair BuiltinData BuiltinData))
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl
             in case BuiltinData -> These a b
f' BuiltinData
v of
                  This a
l' -> (BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k (a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData a
l')) BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls', BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs')
                  That b
r' -> (BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls', BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k (b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData b
r')) BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs')
                  These a
l' b
r' ->
                    ( BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k (a -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData a
l')) BuiltinList (BuiltinPair BuiltinData BuiltinData)
ls'
                    , BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k (b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData b
r')) BuiltinList (BuiltinPair BuiltinData BuiltinData)
rs'
                    )
        )
    f' :: BuiltinData -> These a b
    f' :: BuiltinData -> These a b
f' = v -> These a b
f (v -> These a b) -> (BuiltinData -> v) -> BuiltinData -> These a b
forall b c a. (b -> c) -> (a -> b) -> a -> c
. BuiltinData -> v
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData

{-# INLINEABLE map #-}
map :: forall k a b. (P.UnsafeFromData a, P.ToData b) => (a -> b) -> Map k a -> Map k b
map :: forall k a b.
(UnsafeFromData a, ToData b) =>
(a -> b) -> Map k a -> Map k b
map a -> b
f (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k b
forall k a.
BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k a
Map (BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k b)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData) -> Map k b
forall a b. (a -> b) -> a -> b
$ BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
  where
    go :: BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs =
      BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> (() -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> (BuiltinPair BuiltinData BuiltinData
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
    -> BuiltinList (BuiltinPair BuiltinData BuiltinData))
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair BuiltinData BuiltinData)
xs
        (\() -> BuiltinList (BuiltinPair BuiltinData BuiltinData)
nil)
        ( \BuiltinPair BuiltinData BuiltinData
hd BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl ->
            let k :: BuiltinData
k = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> a
BI.fst BuiltinPair BuiltinData BuiltinData
hd
                v :: BuiltinData
v = BuiltinPair BuiltinData BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair BuiltinData BuiltinData
hd
             in
              BuiltinPair BuiltinData BuiltinData
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
forall a. a -> BuiltinList a -> BuiltinList a
BI.mkCons
                (BuiltinData -> BuiltinData -> BuiltinPair BuiltinData BuiltinData
BI.mkPairData BuiltinData
k (b -> BuiltinData
forall a. ToData a => a -> BuiltinData
P.toBuiltinData (a -> b
f (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v))))
                (BuiltinList (BuiltinPair BuiltinData BuiltinData)
-> BuiltinList (BuiltinPair BuiltinData BuiltinData)
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
tl)
        )

{-# INLINEABLE foldr #-}
foldr :: forall a b k. (P.UnsafeFromData a) => (a -> b -> b) -> b -> Map k a -> b
foldr :: forall a b k.
UnsafeFromData a =>
(a -> b -> b) -> b -> Map k a -> b
foldr a -> b -> b
f b
z (Map BuiltinList (BuiltinPair BuiltinData BuiltinData)
m) = BuiltinList (BuiltinPair BuiltinData BuiltinData) -> b
forall {a}. BuiltinList (BuiltinPair a BuiltinData) -> b
go BuiltinList (BuiltinPair BuiltinData BuiltinData)
m
  where
    go :: BuiltinList (BuiltinPair a BuiltinData) -> b
go BuiltinList (BuiltinPair a BuiltinData)
xs =
      BuiltinList (BuiltinPair a BuiltinData)
-> (() -> b)
-> (BuiltinPair a BuiltinData
    -> BuiltinList (BuiltinPair a BuiltinData) -> b)
-> b
forall a r.
BuiltinList a -> (() -> r) -> (a -> BuiltinList a -> r) -> r
P.matchList
        BuiltinList (BuiltinPair a BuiltinData)
xs
        (\() -> b
z)
        ( \BuiltinPair a BuiltinData
hd BuiltinList (BuiltinPair a BuiltinData)
tl ->
            let v :: BuiltinData
v = BuiltinPair a BuiltinData -> BuiltinData
forall a b. BuiltinPair a b -> b
BI.snd BuiltinPair a BuiltinData
hd
             in a -> b -> b
f (BuiltinData -> a
forall a. UnsafeFromData a => BuiltinData -> a
P.unsafeFromBuiltinData BuiltinData
v) (BuiltinList (BuiltinPair a BuiltinData) -> b
go BuiltinList (BuiltinPair a BuiltinData)
tl)
        )

makeLift ''Map