{-# LANGUAGE CPP
            ,MultiParamTypeClasses
            ,FlexibleContexts
            ,FlexibleInstances
            ,TypeFamilies
            ,UndecidableInstances #-}
{-# LANGUAGE TypeOperators #-}  -- for GHC >= 9.4
#if __GLASGOW_HASKELL__ < 710
{-# LANGUAGE OverlappingInstances #-}
#endif
{-# OPTIONS -fno-warn-orphans #-}

-- | ListLike instance for any type supporting the @Data.Vector.Generic@
-- interface.  To avoid collisions with other Vector instances, this module
-- must be imported directly.
module Data.ListLike.Vector.Generic ()

where

import           Prelude as P
import qualified Data.Vector.Generic as V
import           Data.Vector.Generic ((!))
import           Data.ListLike.Base
import           Data.ListLike.FoldableLL
import           Data.ListLike.String
import           Data.String (IsString)
import           GHC.Exts (IsList(..))

instance {-# OVERLAPPABLE #-} V.Vector v a => FoldableLL (v a) a where
    foldl :: forall a. (a -> a -> a) -> a -> v a -> a
foldl = forall (v :: * -> *) b a.
Vector v b =>
(a -> b -> a) -> a -> v b -> a
V.foldl
    foldl' :: forall a. (a -> a -> a) -> a -> v a -> a
foldl' = forall (v :: * -> *) b a.
Vector v b =>
(a -> b -> a) -> a -> v b -> a
V.foldl'
    foldl1 :: (a -> a -> a) -> v a -> a
foldl1 = forall (v :: * -> *) a. Vector v a => (a -> a -> a) -> v a -> a
V.foldl1
    foldr :: forall b. (a -> b -> b) -> b -> v a -> b
foldr = forall (v :: * -> *) a b.
Vector v a =>
(a -> b -> b) -> b -> v a -> b
V.foldr
    foldr' :: forall b. (a -> b -> b) -> b -> v a -> b
foldr' = forall (v :: * -> *) a b.
Vector v a =>
(a -> b -> b) -> b -> v a -> b
V.foldr'
    foldr1 :: (a -> a -> a) -> v a -> a
foldr1 = forall (v :: * -> *) a. Vector v a => (a -> a -> a) -> v a -> a
V.foldr1

#if 0
instance {-# OVERLAPPABLE #-} (Monoid (v a), Eq (v a), V.Vector v a) => IsList (v a) where
    type Item (v a) = a
    toList = V.toList
    fromList = V.fromList
#endif

instance {-# OVERLAPPABLE #-} (IsList (v a), Item (v a) ~ a, Monoid (v a), Eq (v a), V.Vector v a) => ListLike (v a) a where
    empty :: v a
empty = forall (v :: * -> *) a. Vector v a => v a
V.empty
    singleton :: a -> v a
singleton = forall (v :: * -> *) a. Vector v a => a -> v a
V.singleton
    cons :: a -> v a -> v a
cons = forall (v :: * -> *) a. Vector v a => a -> v a -> v a
V.cons
    snoc :: v a -> a -> v a
snoc = forall (v :: * -> *) a. Vector v a => v a -> a -> v a
V.snoc
    append :: v a -> v a -> v a
append = forall a. Monoid a => a -> a -> a
mappend
    head :: v a -> a
head = forall (v :: * -> *) a. Vector v a => v a -> a
V.head
    last :: v a -> a
last = forall (v :: * -> *) a. Vector v a => v a -> a
V.last
    tail :: v a -> v a
tail = forall (v :: * -> *) a. Vector v a => v a -> v a
V.tail
    init :: v a -> v a
init = forall (v :: * -> *) a. Vector v a => v a -> v a
V.init
    null :: v a -> Bool
null = forall (v :: * -> *) a. Vector v a => v a -> Bool
V.null
    length :: v a -> Int
length = forall (v :: * -> *) a. Vector v a => v a -> Int
V.length
    rigidMap :: (a -> a) -> v a -> v a
rigidMap = forall (v :: * -> *) a b.
(Vector v a, Vector v b) =>
(a -> b) -> v a -> v b
V.map
    reverse :: v a -> v a
reverse = forall (v :: * -> *) a. Vector v a => v a -> v a
V.reverse
    --intersperse =
    concat :: forall full'. ListLike full' (v a) => full' -> v a
concat = forall (v :: * -> *) a. Vector v a => [v a] -> v a
V.concat forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall l. IsList l => l -> [Item l]
toList
    rigidConcatMap :: (a -> v a) -> v a -> v a
rigidConcatMap = forall (v :: * -> *) a b.
(Vector v a, Vector v b) =>
(a -> v b) -> v a -> v b
V.concatMap
    any :: (a -> Bool) -> v a -> Bool
any = forall (v :: * -> *) a. Vector v a => (a -> Bool) -> v a -> Bool
V.any
    all :: (a -> Bool) -> v a -> Bool
all = forall (v :: * -> *) a. Vector v a => (a -> Bool) -> v a -> Bool
V.all
    maximum :: Ord a => v a -> a
maximum = forall (v :: * -> *) a. (Vector v a, Ord a) => v a -> a
V.maximum
    minimum :: Ord a => v a -> a
minimum = forall (v :: * -> *) a. (Vector v a, Ord a) => v a -> a
V.minimum
    replicate :: Int -> a -> v a
replicate = forall (v :: * -> *) a. Vector v a => Int -> a -> v a
V.replicate
    take :: Int -> v a -> v a
take = forall (v :: * -> *) a. Vector v a => Int -> v a -> v a
V.take
    drop :: Int -> v a -> v a
drop = forall (v :: * -> *) a. Vector v a => Int -> v a -> v a
V.drop
    --splitAt =
    takeWhile :: (a -> Bool) -> v a -> v a
takeWhile = forall (v :: * -> *) a. Vector v a => (a -> Bool) -> v a -> v a
V.takeWhile
    dropWhile :: (a -> Bool) -> v a -> v a
dropWhile = forall (v :: * -> *) a. Vector v a => (a -> Bool) -> v a -> v a
V.dropWhile
    span :: (a -> Bool) -> v a -> (v a, v a)
span = forall (v :: * -> *) a.
Vector v a =>
(a -> Bool) -> v a -> (v a, v a)
V.span
    break :: (a -> Bool) -> v a -> (v a, v a)
break = forall (v :: * -> *) a.
Vector v a =>
(a -> Bool) -> v a -> (v a, v a)
V.break
    --group =
    --inits =
    --tails =
    isPrefixOf :: Eq a => v a -> v a -> Bool
isPrefixOf = forall (v :: * -> *) a.
(Vector v a, Eq (v a)) =>
v a -> v a -> Bool
isPrefixOf'
    isSuffixOf :: Eq a => v a -> v a -> Bool
isSuffixOf = forall (v :: * -> *) a.
(Vector v a, Eq (v a)) =>
v a -> v a -> Bool
isSuffixOf'
    elem :: Eq a => a -> v a -> Bool
elem = forall (v :: * -> *) a. (Vector v a, Eq a) => a -> v a -> Bool
V.elem
    find :: (a -> Bool) -> v a -> Maybe a
find = forall (v :: * -> *) a. Vector v a => (a -> Bool) -> v a -> Maybe a
V.find
    filter :: (a -> Bool) -> v a -> v a
filter = forall (v :: * -> *) a. Vector v a => (a -> Bool) -> v a -> v a
V.filter
    index :: v a -> Int -> a
index = forall (v :: * -> *) a.
(HasCallStack, Vector v a) =>
v a -> Int -> a
(!)
    findIndex :: (a -> Bool) -> v a -> Maybe Int
findIndex = forall (v :: * -> *) a.
Vector v a =>
(a -> Bool) -> v a -> Maybe Int
V.findIndex
    --toList = V.toList
    --fromList = V.fromList
    --fromListLike = fromList . toList
    --groupBy f =
    genericLength :: forall a. Num a => v a -> a
genericLength = forall a. Num a => Integer -> a
fromInteger forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a b. (Integral a, Num b) => a -> b
fromIntegral forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall (v :: * -> *) a. Vector v a => v a -> Int
V.length
    genericTake :: forall a. Integral a => a -> v a -> v a
genericTake a
i = forall (v :: * -> *) a. Vector v a => Int -> v a -> v a
V.take (forall a b. (Integral a, Num b) => a -> b
fromIntegral a
i)
    genericDrop :: forall a. Integral a => a -> v a -> v a
genericDrop a
i = forall (v :: * -> *) a. Vector v a => Int -> v a -> v a
V.drop (forall a b. (Integral a, Num b) => a -> b
fromIntegral a
i)
    --genericSplitAt i =
    genericReplicate :: forall a. Integral a => a -> a -> v a
genericReplicate a
i = forall (v :: * -> *) a. Vector v a => Int -> a -> v a
V.replicate (forall a b. (Integral a, Num b) => a -> b
fromIntegral a
i)

    sequence :: forall (m :: * -> *) fullinp.
(Applicative m, ListLike fullinp (m a)) =>
fullinp -> m (v a)
sequence  = forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap forall l. IsList l => [Item l] -> l
fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall (t :: * -> *) (f :: * -> *) a.
(Traversable t, Applicative f) =>
t (f a) -> f (t a)
P.sequenceA  forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall l. IsList l => l -> [Item l]
toList
    mapM :: forall (m :: * -> *) full' item'.
(Applicative m, ListLike full' item') =>
(a -> m item') -> v a -> m full'
mapM a -> m item'
func = forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
fmap forall l. IsList l => [Item l] -> l
fromList forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall (t :: * -> *) (f :: * -> *) a b.
(Traversable t, Applicative f) =>
(a -> f b) -> t a -> f (t b)
P.traverse a -> m item'
func forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall l. IsList l => l -> [Item l]
toList

instance (Eq (v Char), V.Vector v Char) => IsString (v Char) where
    fromString :: String -> v Char
fromString = forall (v :: * -> *) a. Vector v a => [a] -> v a
V.fromList

instance (Eq (v Char), V.Vector v Char) => StringLike (v Char) where
    toString :: v Char -> String
toString = forall (v :: * -> *) a. Vector v a => v a -> [a]
V.toList
    --words =
    --lines =
    unwords :: forall full. ListLike full (v Char) => full -> v Char
unwords = let sp :: v Char
sp = forall (v :: * -> *) a. Vector v a => a -> v a
V.singleton Char
' ' in forall (v :: * -> *) a. Vector v a => [v a] -> v a
V.concat forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall full item. ListLike full item => item -> full -> full
intersperse v Char
sp forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall l. IsList l => l -> [Item l]
toList
    unlines :: forall full. ListLike full (v Char) => full -> v Char
unlines = let eol :: v Char
eol = forall (v :: * -> *) a. Vector v a => a -> v a
V.singleton Char
'\n' in forall (v :: * -> *) a. Vector v a => [v a] -> v a
V.concat forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall full item. ListLike full item => item -> full -> full
intersperse v Char
eol forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall l. IsList l => l -> [Item l]
toList

isPrefixOf' :: (V.Vector v a, Eq (v a)) => v a -> v a -> Bool
isPrefixOf' :: forall (v :: * -> *) a.
(Vector v a, Eq (v a)) =>
v a -> v a -> Bool
isPrefixOf' v a
needle v a
haystack
  | forall (v :: * -> *) a. Vector v a => v a -> Bool
V.null v a
needle = Bool
True
  | forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle forall a. Ord a => a -> a -> Bool
< forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
haystack =
            v a
needle forall a. Eq a => a -> a -> Bool
== forall (v :: * -> *) a.
(HasCallStack, Vector v a) =>
Int -> Int -> v a -> v a
V.slice Int
0 (forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle) v a
haystack
  | forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle forall a. Eq a => a -> a -> Bool
== forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
haystack = v a
needle forall a. Eq a => a -> a -> Bool
== v a
haystack
  | Bool
otherwise = Bool
False
isSuffixOf' :: (V.Vector v a, Eq (v a)) => v a -> v a -> Bool
isSuffixOf' :: forall (v :: * -> *) a.
(Vector v a, Eq (v a)) =>
v a -> v a -> Bool
isSuffixOf' v a
needle v a
haystack
  | forall (v :: * -> *) a. Vector v a => v a -> Bool
V.null v a
needle = Bool
True
  | forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle forall a. Ord a => a -> a -> Bool
< forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
haystack =
        v a
needle forall a. Eq a => a -> a -> Bool
== forall (v :: * -> *) a.
(HasCallStack, Vector v a) =>
Int -> Int -> v a -> v a
V.slice (forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
haystack forall a. Num a => a -> a -> a
- forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle)
                          (forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle)
                          v a
haystack
  | forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
needle forall a. Eq a => a -> a -> Bool
== forall (v :: * -> *) a. Vector v a => v a -> Int
V.length v a
haystack = v a
needle forall a. Eq a => a -> a -> Bool
== v a
haystack
  | Bool
otherwise = Bool
False