-- Copyright 2018-2021 Google LLC
--
-- Licensed under the Apache License, Version 2.0 (the "License");
-- you may not use this file except in compliance with the License.
-- You may obtain a copy of the License at
--
--      http://www.apache.org/licenses/LICENSE-2.0
--
-- Unless required by applicable law or agreed to in writing, software
-- distributed under the License is distributed on an "AS IS" BASIS,
-- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-- See the License for the specific language governing permissions and
-- limitations under the License.

-- | Provides an analog of @Representable@ over arity-1 type constructors.

{-# LANGUAGE AllowAmbiguousTypes #-}
{-# LANGUAGE ConstraintKinds #-}
{-# LANGUAGE DeriveGeneric #-}
{-# LANGUAGE DerivingStrategies #-}
{-# LANGUAGE DerivingVia #-}
{-# LANGUAGE FlexibleContexts #-}
{-# LANGUAGE FlexibleInstances #-}
{-# LANGUAGE GeneralizedNewtypeDeriving #-}
{-# LANGUAGE PolyKinds #-}
{-# LANGUAGE RankNTypes #-}
{-# LANGUAGE ScopedTypeVariables #-}
{-# LANGUAGE StandaloneDeriving #-}
{-# LANGUAGE TypeApplications #-}
{-# LANGUAGE TypeFamilies #-}
{-# LANGUAGE TypeOperators #-}
{-# LANGUAGE UndecidableInstances #-}

module Data.Ten.Representable
         ( Representable10(..)
         , rep10', field10'
         , distributeRep10, collectRep10
         , GTabulate10(..)
         , index10C
         ) where

import Data.Coerce (coerce)
import Data.Functor.Const (Const(..))
import Data.Kind (Type)
import Data.Type.Equality ((:~:)(..))
import GHC.Generics
         ( Generic1(..)
         , (:.:)(..), (:*:)(..)
         , M1(..), Rec1(..), U1(..)
         )

import Data.Wrapped (Wrapped1(..))

import Data.Functor.Rep (Representable(..))
import Data.Ten.Ap (Ap10(..))
import Data.Ten.Applicative (Applicative10(..))
import Data.Ten.Entails (Entails(..), withEntailment)
import Data.Ten.Field (Field10(..))
import Data.Ten.Functor (Functor10(..))
import Data.Ten.Functor.WithIndex (Index10, Functor10WithIndex(..))
import Data.Ten.Foldable (Foldable10(..), fold10)
import Data.Ten.Foldable.WithIndex (Foldable10WithIndex(..))
import Data.Ten.Internal (starFst, starSnd)
import Data.Ten.Traversable (Traversable10(..))
import Data.Ten.Traversable.WithIndex (Traversable10WithIndex(..))

(.:) :: (q -> r) -> (a -> b -> q) -> a -> b -> r
.: :: (q -> r) -> (a -> b -> q) -> a -> b -> r
(.:) = ((b -> q) -> b -> r) -> (a -> b -> q) -> a -> b -> r
forall b c a. (b -> c) -> (a -> b) -> a -> c
(.) (((b -> q) -> b -> r) -> (a -> b -> q) -> a -> b -> r)
-> ((q -> r) -> (b -> q) -> b -> r)
-> (q -> r)
-> (a -> b -> q)
-> a
-> b
-> r
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (q -> r) -> (b -> q) -> b -> r
forall b c a. (b -> c) -> (a -> b) -> a -> c
(.)

-- | Analog of 'Data.Functor.Rep.Representable' over arity-1 type constructors.
--
-- If @f@ is @Representable10@, then a value of type @f m@ is isomorphic to a
-- function @forall a. Rep10 f a -> m a@.  This essentially means it can be
-- thought of as a fixed-shape record with a wrapper type applied to all of its
-- fields.
--
-- This is also equivalent to a total dependent map from @Rep10 f@ to @m@
-- ("total" meaning that every "key" has a "value").
class Applicative10 f => Representable10 (f :: (k -> Type) -> Type) where
  -- | The "index" type of an @f@ "container".
  --
  -- This is a type that behaves like a GADT, with a value for each possible
  -- "position" of an @m a@ in @f m@ and the parameter type(s) @a@ it can have.
  type Rep10 f :: k -> Type

  -- | Given an @f m@ and a @Rep10 f a@ "index" into it, extract the @m a@.
  index10 :: f m -> Rep10 f a -> m a

  -- | Build an @f m@ by applying a parametric function to each "index".
  tabulate10 :: (forall a. Rep10 f a -> m a) -> f m

-- | Turn a record field selector into a 'Rep10'.
--
-- See also 'Data.Ten.Lens.rep10'.
rep10' :: Representable10 f => (f (Rep10 f) -> Rep10 f a) -> Rep10 f a
rep10' :: (f (Rep10 f) -> Rep10 f a) -> Rep10 f a
rep10' = ((f (Rep10 f) -> Rep10 f a) -> f (Rep10 f) -> Rep10 f a
forall a b. (a -> b) -> a -> b
$ (forall (a :: k). Rep10 f a -> Rep10 f a) -> f (Rep10 f)
forall k (f :: (k -> *) -> *) (m :: k -> *).
Representable10 f =>
(forall (a :: k). Rep10 f a -> m a) -> f m
tabulate10 forall (a :: k). Rep10 f a -> Rep10 f a
forall a. a -> a
id)

-- | Turn a record field selector targeting 'Ap10' into a 'Rep10'.
--
-- See also 'Data.Ten.Lens.rep10'.
field10'
  :: Representable10 rec
  => (rec (Rep10 rec) -> Ap10 a (Rep10 rec)) -> Rep10 rec a
field10' :: (rec (Rep10 rec) -> Ap10 a (Rep10 rec)) -> Rep10 rec a
field10' rec (Rep10 rec) -> Ap10 a (Rep10 rec)
f = (rec (Rep10 rec) -> Rep10 rec a) -> Rep10 rec a
forall k (f :: (k -> *) -> *) (a :: k).
Representable10 f =>
(f (Rep10 f) -> Rep10 f a) -> Rep10 f a
rep10' (Ap10 a (Rep10 rec) -> Rep10 rec a
forall k (a :: k) (f :: k -> *). Ap10 a f -> f a
unAp10 (Ap10 a (Rep10 rec) -> Rep10 rec a)
-> (rec (Rep10 rec) -> Ap10 a (Rep10 rec))
-> rec (Rep10 rec)
-> Rep10 rec a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. rec (Rep10 rec) -> Ap10 a (Rep10 rec)
f)

-- | Superclass appeasement; deriving via this will give infinite loops; don't!
instance Functor10 f => Functor10 (Wrapped1 Representable10 f) where
  fmap10 :: (forall (a :: k). m a -> n a)
-> Wrapped1 Representable10 f m -> Wrapped1 Representable10 f n
fmap10 forall (a :: k). m a -> n a
f (Wrapped1 f m
fm) = f n -> Wrapped1 Representable10 f n
forall k (c :: (k -> *) -> Constraint) (f :: k -> *) (a :: k).
f a -> Wrapped1 c f a
Wrapped1 ((forall (a :: k). m a -> n a) -> f m -> f n
forall k (f :: (k -> *) -> *) (m :: k -> *) (n :: k -> *).
Functor10 f =>
(forall (a :: k). m a -> n a) -> f m -> f n
fmap10 forall (a :: k). m a -> n a
f f m
fm)

-- | Superclass appeasement; deriving via this will give infinite loops; don't!
instance Foldable10 f => Foldable10 (Wrapped1 Representable10 f) where
  foldMap10 :: (forall (a :: k). m a -> w) -> Wrapped1 Representable10 f m -> w
foldMap10 forall (a :: k). m a -> w
f (Wrapped1 f m
fm) = (forall (a :: k). m a -> w) -> f m -> w
forall k (t :: (k -> *) -> *) w (m :: k -> *).
(Foldable10 t, Monoid w) =>
(forall (a :: k). m a -> w) -> t m -> w
foldMap10 forall (a :: k). m a -> w
f f m
fm

-- | Superclass appeasement; deriving via this will give infinite loops; don't!
instance Traversable10 f => Traversable10 (Wrapped1 Representable10 f) where
  mapTraverse10 :: (Wrapped1 Representable10 f n -> r)
-> (forall (a :: k). m a -> f (n a))
-> Wrapped1 Representable10 f m
-> f r
mapTraverse10 Wrapped1 Representable10 f n -> r
r forall (a :: k). m a -> f (n a)
f (Wrapped1 f m
fm) = (f n -> r) -> (forall (a :: k). m a -> f (n a)) -> f m -> f r
forall k (t :: (k -> *) -> *) (f :: * -> *) (m :: k -> *)
       (n :: k -> *) r.
(Traversable10 t, Applicative f) =>
(t n -> r) -> (forall (a :: k). m a -> f (n a)) -> t m -> f r
mapTraverse10 (Wrapped1 Representable10 f n -> r
r (Wrapped1 Representable10 f n -> r)
-> (f n -> Wrapped1 Representable10 f n) -> f n -> r
forall b c a. (b -> c) -> (a -> b) -> a -> c
. f n -> Wrapped1 Representable10 f n
forall k (c :: (k -> *) -> Constraint) (f :: k -> *) (a :: k).
f a -> Wrapped1 c f a
Wrapped1) forall (a :: k). m a -> f (n a)
f f m
fm

type instance Index10 (Wrapped1 Representable10 f) = Rep10 f

instance Representable10 f
      => Functor10WithIndex (Wrapped1 Representable10 f) where
  imap10 :: (forall (a :: k).
 Index10 (Wrapped1 Representable10 f) a -> m a -> n a)
-> Wrapped1 Representable10 f m -> Wrapped1 Representable10 f n
imap10 forall (a :: k).
Index10 (Wrapped1 Representable10 f) a -> m a -> n a
f (Wrapped1 f m
fm) = f n -> Wrapped1 Representable10 f n
forall k (c :: (k -> *) -> Constraint) (f :: k -> *) (a :: k).
f a -> Wrapped1 c f a
Wrapped1 (f n -> Wrapped1 Representable10 f n)
-> f n -> Wrapped1 Representable10 f n
forall a b. (a -> b) -> a -> b
$ (forall (a :: k). Rep10 f a -> n a) -> f n
forall k (f :: (k -> *) -> *) (m :: k -> *).
Representable10 f =>
(forall (a :: k). Rep10 f a -> m a) -> f m
tabulate10 (\Rep10 f a
i -> Index10 (Wrapped1 Representable10 f) a -> m a -> n a
forall (a :: k).
Index10 (Wrapped1 Representable10 f) a -> m a -> n a
f Index10 (Wrapped1 Representable10 f) a
Rep10 f a
i (f m
fm f m -> Rep10 f a -> m a
forall k (f :: (k -> *) -> *) (m :: k -> *) (a :: k).
Representable10 f =>
f m -> Rep10 f a -> m a
`index10` Rep10 f a
i))

instance (Representable10 f, Foldable10 f)
      => Foldable10WithIndex (Wrapped1 Representable10 f) where
  ifoldMap10 :: (forall (a :: k).
 Index10 (Wrapped1 Representable10 f) a -> m a -> w)
-> Wrapped1 Representable10 f m -> w
ifoldMap10 forall (a :: k). Index10 (Wrapped1 Representable10 f) a -> m a -> w
f Wrapped1 Representable10 f m
fm = Wrapped1 Representable10 f (Const w) -> w
forall k (t :: (k -> *) -> *) m.
(Foldable10 t, Monoid m) =>
t (Const m) -> m
fold10 (Wrapped1 Representable10 f (Const w) -> w)
-> Wrapped1 Representable10 f (Const w) -> w
forall a b. (a -> b) -> a -> b
$ (forall (a :: k).
 Index10 (Wrapped1 Representable10 f) a -> m a -> Const w a)
-> Wrapped1 Representable10 f m
-> Wrapped1 Representable10 f (Const w)
forall k (f :: (k -> *) -> *) (m :: k -> *) (n :: k -> *).
Functor10WithIndex f =>
(forall (a :: k). Index10 f a -> m a -> n a) -> f m -> f n
imap10 (w -> Const w a
forall k a (b :: k). a -> Const a b
Const (w -> Const w a)
-> (Rep10 f a -> m a -> w) -> Rep10 f a -> m a -> Const w a
forall q r a b. (q -> r) -> (a -> b -> q) -> a -> b -> r
.: Rep10 f a -> m a -> w
forall (a :: k). Index10 (Wrapped1 Representable10 f) a -> m a -> w
f) Wrapped1 Representable10 f m
fm

instance (Representable10 f, Traversable10 f)
      => Traversable10WithIndex (Wrapped1 Representable10 f) where
  imapTraverse10 :: (Wrapped1 Representable10 f n -> r)
-> (forall (a :: k).
    Index10 (Wrapped1 Representable10 f) a -> m a -> g (n a))
-> Wrapped1 Representable10 f m
-> g r
imapTraverse10 Wrapped1 Representable10 f n -> r
r forall (a :: k).
Index10 (Wrapped1 Representable10 f) a -> m a -> g (n a)
f Wrapped1 Representable10 f m
fm = (Wrapped1 Representable10 f n -> r)
-> (forall (a :: k). (:.:) g n a -> g (n a))
-> Wrapped1 Representable10 f (g :.: n)
-> g r
forall k (t :: (k -> *) -> *) (f :: * -> *) (m :: k -> *)
       (n :: k -> *) r.
(Traversable10 t, Applicative f) =>
(t n -> r) -> (forall (a :: k). m a -> f (n a)) -> t m -> f r
mapTraverse10 Wrapped1 Representable10 f n -> r
r forall (a :: k). (:.:) g n a -> g (n a)
forall k2 (f :: k2 -> *) k1 (g :: k1 -> k2) (p :: k1).
(:.:) f g p -> f (g p)
unComp1 (Wrapped1 Representable10 f (g :.: n) -> g r)
-> Wrapped1 Representable10 f (g :.: n) -> g r
forall a b. (a -> b) -> a -> b
$ (forall (a :: k).
 Index10 (Wrapped1 Representable10 f) a -> m a -> (:.:) g n a)
-> Wrapped1 Representable10 f m
-> Wrapped1 Representable10 f (g :.: n)
forall k (f :: (k -> *) -> *) (m :: k -> *) (n :: k -> *).
Functor10WithIndex f =>
(forall (a :: k). Index10 f a -> m a -> n a) -> f m -> f n
imap10 (g (n a) -> (:.:) g n a
forall k2 k1 (f :: k2 -> *) (g :: k1 -> k2) (p :: k1).
f (g p) -> (:.:) f g p
Comp1 (g (n a) -> (:.:) g n a)
-> (Rep10 f a -> m a -> g (n a)) -> Rep10 f a -> m a -> (:.:) g n a
forall q r a b. (q -> r) -> (a -> b -> q) -> a -> b -> r
.: Rep10 f a -> m a -> g (n a)
forall (a :: k).
Index10 (Wrapped1 Representable10 f) a -> m a -> g (n a)
f) Wrapped1 Representable10 f m
fm

-- | Analog of 'Data.Functor.Rep.distributeRep' for 'Representable10'.
--
-- Pulls a fixed record shape to the outside of any functor.
distributeRep10
  :: (Representable10 f, Functor w)
  => w (f m) -> f (w :.: m)
distributeRep10 :: w (f m) -> f (w :.: m)
distributeRep10 w (f m)
wfm = (forall (a :: k1). Rep10 f a -> (:.:) w m a) -> f (w :.: m)
forall k (f :: (k -> *) -> *) (m :: k -> *).
Representable10 f =>
(forall (a :: k). Rep10 f a -> m a) -> f m
tabulate10 (\Rep10 f a
r -> w (m a) -> (:.:) w m a
forall k2 k1 (f :: k2 -> *) (g :: k1 -> k2) (p :: k1).
f (g p) -> (:.:) f g p
Comp1 (w (m a) -> (:.:) w m a) -> w (m a) -> (:.:) w m a
forall a b. (a -> b) -> a -> b
$ (f m -> Rep10 f a -> m a
forall k (f :: (k -> *) -> *) (m :: k -> *) (a :: k).
Representable10 f =>
f m -> Rep10 f a -> m a
`index10` Rep10 f a
r) (f m -> m a) -> w (f m) -> w (m a)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> w (f m)
wfm)

-- | Analog of 'Data.Functor.Rep.collectRep' for 'Representable10'.
--
-- Gathers a fixed record shape mapped over the elements of any functor.
collectRep10
  :: (Representable10 f, Functor w)
  => (a -> f m) -> w a -> f (w :.: m)
collectRep10 :: (a -> f m) -> w a -> f (w :.: m)
collectRep10 a -> f m
f w a
wa = w (f m) -> f (w :.: m)
forall k1 (f :: (k1 -> *) -> *) (w :: * -> *) (m :: k1 -> *).
(Representable10 f, Functor w) =>
w (f m) -> f (w :.: m)
distributeRep10 (a -> f m
f (a -> f m) -> w a -> w (f m)
forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> w a
wa)

-- | The 'Generic1' implementation of 'tabulate10' based on 'Field10'.
class GTabulate10 (rec :: (k -> Type) -> Type) where
  gtabulate10 :: (forall a. Field10 rec a -> r a) -> rec r

instance Representable10 (Ap10 a) where
  type Rep10 (Ap10 a) = (:~:) a
  index10 :: Ap10 a m -> Rep10 (Ap10 a) a -> m a
index10 (Ap10 m a
x) Rep10 (Ap10 a) a
Refl = m a
m a
x
  tabulate10 :: (forall (a :: k). Rep10 (Ap10 a) a -> m a) -> Ap10 a m
tabulate10 forall (a :: k). Rep10 (Ap10 a) a -> m a
f = m a -> Ap10 a m
forall k (a :: k) (f :: k -> *). f a -> Ap10 a f
Ap10 (Rep10 (Ap10 a) a -> m a
forall (a :: k). Rep10 (Ap10 a) a -> m a
f Rep10 (Ap10 a) a
forall k (a :: k). a :~: a
Refl)

instance GTabulate10 U1 where
  gtabulate10 :: (forall (a :: k). Field10 U1 a -> r a) -> U1 r
gtabulate10 forall (a :: k). Field10 U1 a -> r a
_ = U1 r
forall k (p :: k). U1 p
U1
  {-# INLINE gtabulate10 #-}

instance Representable10 rec => GTabulate10 (Rec1 rec) where
  gtabulate10 :: (forall (a :: k). Field10 (Rec1 rec) a -> r a) -> Rec1 rec r
gtabulate10 forall (a :: k). Field10 (Rec1 rec) a -> r a
r = rec r -> Rec1 rec r
forall k (f :: k -> *) (p :: k). f p -> Rec1 f p
Rec1 (rec r -> Rec1 rec r) -> rec r -> Rec1 rec r
forall a b. (a -> b) -> a -> b
$
    (forall (a :: k). Rep10 rec a -> r a) -> rec r
forall k (f :: (k -> *) -> *) (m :: k -> *).
Representable10 f =>
(forall (a :: k). Rep10 f a -> m a) -> f m
tabulate10 (\Rep10 rec a
i -> Field10 (Rec1 rec) a -> r a
forall (a :: k). Field10 (Rec1 rec) a -> r a
r ((forall (m :: k -> *). Rec1 rec m -> m a) -> Field10 (Rec1 rec) a
forall k (f :: (k -> *) -> *) (a :: k).
(forall (m :: k -> *). f m -> m a) -> Field10 f a
Field10 (\ (Rec1 f) -> rec m -> Rep10 rec a -> m a
forall k (f :: (k -> *) -> *) (m :: k -> *) (a :: k).
Representable10 f =>
f m -> Rep10 f a -> m a
index10 rec m
f Rep10 rec a
i)))
  {-# INLINE gtabulate10 #-}

instance GTabulate10 rec => GTabulate10 (M1 k i rec) where
  gtabulate10 :: (forall (a :: k). Field10 (M1 k i rec) a -> r a) -> M1 k i rec r
gtabulate10 forall (a :: k). Field10 (M1 k i rec) a -> r a
r = rec r -> M1 k i rec r
forall k i (c :: Meta) (f :: k -> *) (p :: k). f p -> M1 i c f p
M1 (rec r -> M1 k i rec r) -> rec r -> M1 k i rec r
forall a b. (a -> b) -> a -> b
$ (forall (a :: k). Field10 rec a -> r a) -> rec r
forall k (rec :: (k -> *) -> *) (r :: k -> *).
GTabulate10 rec =>
(forall (a :: k). Field10 rec a -> r a) -> rec r
gtabulate10 (Field10 (M1 k i rec) a -> r a
forall (a :: k). Field10 (M1 k i rec) a -> r a
r (Field10 (M1 k i rec) a -> r a)
-> (Field10 rec a -> Field10 (M1 k i rec) a)
-> Field10 rec a
-> r a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Field10 rec a -> Field10 (M1 k i rec) a
coerce)

instance (GTabulate10 f, GTabulate10 g)
      => GTabulate10 (f :*: g) where
  gtabulate10 :: (forall (a :: k). Field10 (f :*: g) a -> r a) -> (:*:) f g r
gtabulate10 forall (a :: k). Field10 (f :*: g) a -> r a
r = f r
ftab f r -> g r -> (:*:) f g r
forall k (f :: k -> *) (g :: k -> *) (p :: k).
f p -> g p -> (:*:) f g p
:*: g r
gtab
   where
    ftab :: f r
ftab = (forall (a :: k). Field10 f a -> r a) -> f r
forall k (rec :: (k -> *) -> *) (r :: k -> *).
GTabulate10 rec =>
(forall (a :: k). Field10 rec a -> r a) -> rec r
gtabulate10 ((forall (a :: k). Field10 f a -> r a) -> f r)
-> (forall (a :: k). Field10 f a -> r a) -> f r
forall a b. (a -> b) -> a -> b
$ \ (Field10 forall (m :: k -> *). f m -> m a
g) -> Field10 (f :*: g) a -> r a
forall (a :: k). Field10 (f :*: g) a -> r a
r (Field10 (f :*: g) a -> r a) -> Field10 (f :*: g) a -> r a
forall a b. (a -> b) -> a -> b
$ (forall (m :: k -> *). (:*:) f g m -> m a) -> Field10 (f :*: g) a
forall k (f :: (k -> *) -> *) (a :: k).
(forall (m :: k -> *). f m -> m a) -> Field10 f a
Field10 ((forall (m :: k -> *). (:*:) f g m -> m a) -> Field10 (f :*: g) a)
-> (forall (m :: k -> *). (:*:) f g m -> m a)
-> Field10 (f :*: g) a
forall a b. (a -> b) -> a -> b
$ f m -> m a
forall (m :: k -> *). f m -> m a
g (f m -> m a) -> ((:*:) f g m -> f m) -> (:*:) f g m -> m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (:*:) f g m -> f m
forall k (f :: k -> *) (g :: k -> *) (m :: k). (:*:) f g m -> f m
starFst
    gtab :: g r
gtab = (forall (a :: k). Field10 g a -> r a) -> g r
forall k (rec :: (k -> *) -> *) (r :: k -> *).
GTabulate10 rec =>
(forall (a :: k). Field10 rec a -> r a) -> rec r
gtabulate10 ((forall (a :: k). Field10 g a -> r a) -> g r)
-> (forall (a :: k). Field10 g a -> r a) -> g r
forall a b. (a -> b) -> a -> b
$ \ (Field10 forall (m :: k -> *). g m -> m a
g) -> Field10 (f :*: g) a -> r a
forall (a :: k). Field10 (f :*: g) a -> r a
r (Field10 (f :*: g) a -> r a) -> Field10 (f :*: g) a -> r a
forall a b. (a -> b) -> a -> b
$ (forall (m :: k -> *). (:*:) f g m -> m a) -> Field10 (f :*: g) a
forall k (f :: (k -> *) -> *) (a :: k).
(forall (m :: k -> *). f m -> m a) -> Field10 f a
Field10 ((forall (m :: k -> *). (:*:) f g m -> m a) -> Field10 (f :*: g) a)
-> (forall (m :: k -> *). (:*:) f g m -> m a)
-> Field10 (f :*: g) a
forall a b. (a -> b) -> a -> b
$ g m -> m a
forall (m :: k -> *). g m -> m a
g (g m -> m a) -> ((:*:) f g m -> g m) -> (:*:) f g m -> m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (:*:) f g m -> g m
forall k (f :: k -> *) (g :: k -> *) (m :: k). (:*:) f g m -> g m
starSnd
  {-# INLINE gtabulate10 #-}

instance (Representable f, GTabulate10 g) => GTabulate10 (f :.: g) where
  gtabulate10 :: (forall (a :: k). Field10 (f :.: g) a -> r a) -> (:.:) f g r
gtabulate10 forall (a :: k). Field10 (f :.: g) a -> r a
r = f (g r) -> (:.:) f g r
forall k2 k1 (f :: k2 -> *) (g :: k1 -> k2) (p :: k1).
f (g p) -> (:.:) f g p
Comp1 (f (g r) -> (:.:) f g r) -> f (g r) -> (:.:) f g r
forall a b. (a -> b) -> a -> b
$
    (Rep f -> g r) -> f (g r)
forall (f :: * -> *) a. Representable f => (Rep f -> a) -> f a
tabulate ((Rep f -> g r) -> f (g r)) -> (Rep f -> g r) -> f (g r)
forall a b. (a -> b) -> a -> b
$ \ Rep f
i ->
    (forall (a :: k). Field10 g a -> r a) -> g r
forall k (rec :: (k -> *) -> *) (r :: k -> *).
GTabulate10 rec =>
(forall (a :: k). Field10 rec a -> r a) -> rec r
gtabulate10 ((forall (a :: k). Field10 g a -> r a) -> g r)
-> (forall (a :: k). Field10 g a -> r a) -> g r
forall a b. (a -> b) -> a -> b
$ \ (Field10 forall (m :: k -> *). g m -> m a
g) ->
    Field10 (f :.: g) a -> r a
forall (a :: k). Field10 (f :.: g) a -> r a
r (Field10 (f :.: g) a -> r a) -> Field10 (f :.: g) a -> r a
forall a b. (a -> b) -> a -> b
$ (forall (m :: k -> *). (:.:) f g m -> m a) -> Field10 (f :.: g) a
forall k (f :: (k -> *) -> *) (a :: k).
(forall (m :: k -> *). f m -> m a) -> Field10 f a
Field10 (g m -> m a
forall (m :: k -> *). g m -> m a
g (g m -> m a) -> ((:.:) f g m -> g m) -> (:.:) f g m -> m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (f (g m) -> Rep f -> g m) -> Rep f -> f (g m) -> g m
forall a b c. (a -> b -> c) -> b -> a -> c
flip f (g m) -> Rep f -> g m
forall (f :: * -> *) a. Representable f => f a -> Rep f -> a
index Rep f
i (f (g m) -> g m) -> ((:.:) f g m -> f (g m)) -> (:.:) f g m -> g m
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (:.:) f g m -> f (g m)
forall k2 (f :: k2 -> *) k1 (g :: k1 -> k2) (p :: k1).
(:.:) f g p -> f (g p)
unComp1)
  {-# INLINE gtabulate10 #-}

instance (Generic1 rec, Applicative10 (Rep1 rec), GTabulate10 (Rep1 rec))
      => Representable10 (Wrapped1 Generic1 rec) where
  type Rep10 (Wrapped1 Generic1 rec) = Field10 rec
  index10 :: Wrapped1 Generic1 rec m -> Rep10 (Wrapped1 Generic1 rec) a -> m a
index10 (Wrapped1 rec m
rec) (Field10 f) = rec m -> m a
forall (m :: k -> *). rec m -> m a
f rec m
rec
  tabulate10 :: (forall (a :: k). Rep10 (Wrapped1 Generic1 rec) a -> m a)
-> Wrapped1 Generic1 rec m
tabulate10 forall (a :: k). Rep10 (Wrapped1 Generic1 rec) a -> m a
f =
    rec m -> Wrapped1 Generic1 rec m
forall k (c :: (k -> *) -> Constraint) (f :: k -> *) (a :: k).
f a -> Wrapped1 c f a
Wrapped1 (rec m -> Wrapped1 Generic1 rec m)
-> rec m -> Wrapped1 Generic1 rec m
forall a b. (a -> b) -> a -> b
$ Rep1 rec m -> rec m
forall k (f :: k -> *) (a :: k). Generic1 f => Rep1 f a -> f a
to1 (Rep1 rec m -> rec m) -> Rep1 rec m -> rec m
forall a b. (a -> b) -> a -> b
$ (forall (a :: k). Field10 (Rep1 rec) a -> m a) -> Rep1 rec m
forall k (rec :: (k -> *) -> *) (r :: k -> *).
GTabulate10 rec =>
(forall (a :: k). Field10 rec a -> r a) -> rec r
gtabulate10 ((forall (a :: k). Field10 (Rep1 rec) a -> m a) -> Rep1 rec m)
-> (forall (a :: k). Field10 (Rep1 rec) a -> m a) -> Rep1 rec m
forall a b. (a -> b) -> a -> b
$ \Field10 (Rep1 rec) a
i -> Rep10 (Wrapped1 Generic1 rec) a -> m a
forall (a :: k). Rep10 (Wrapped1 Generic1 rec) a -> m a
f (Rep10 (Wrapped1 Generic1 rec) a -> m a)
-> Rep10 (Wrapped1 Generic1 rec) a -> m a
forall a b. (a -> b) -> a -> b
$ (forall (m :: k -> *). rec m -> m a) -> Field10 rec a
forall k (f :: (k -> *) -> *) (a :: k).
(forall (m :: k -> *). f m -> m a) -> Field10 f a
Field10 ((forall (m :: k -> *). rec m -> m a) -> Field10 rec a)
-> (forall (m :: k -> *). rec m -> m a) -> Field10 rec a
forall a b. (a -> b) -> a -> b
$ Field10 (Rep1 rec) a -> forall (m :: k -> *). Rep1 rec m -> m a
forall k (f :: (k -> *) -> *) (a :: k).
Field10 f a -> forall (m :: k -> *). f m -> m a
getField10 Field10 (Rep1 rec) a
i (Rep1 rec m -> m a) -> (rec m -> Rep1 rec m) -> rec m -> m a
forall b c a. (b -> c) -> (a -> b) -> a -> c
. rec m -> Rep1 rec m
forall k (f :: k -> *) (a :: k). Generic1 f => f a -> Rep1 f a
from1

-- | Access an element along with an instance for its type parameter.
index10C
  :: forall c f a r m
   . (Representable10 f, Entails (Rep10 f) c)
  => f m -> Rep10 f a -> (c a => m a -> r) -> r
index10C :: f m -> Rep10 f a -> (c a => m a -> r) -> r
index10C f m
fm Rep10 f a
k c a => m a -> r
f = Rep10 f a -> (c a => r) -> r
forall k1 (c :: k1 -> Constraint) (k2 :: k1 -> *) (a :: k1) r.
Entails k2 c =>
k2 a -> (c a => r) -> r
withEntailment @c Rep10 f a
k ((c a => r) -> r) -> (c a => r) -> r
forall a b. (a -> b) -> a -> b
$ c a => m a -> r
m a -> r
f (f m -> Rep10 f a -> m a
forall k (f :: (k -> *) -> *) (m :: k -> *) (a :: k).
Representable10 f =>
f m -> Rep10 f a -> m a
index10 f m
fm Rep10 f a
k)