-- Hoogle documentation, generated by Haddock
-- See Hoogle, http://www.haskell.org/hoogle/


-- | Dependent sum type
--   
--   A dependent sum is a generalization of a particular way of thinking
--   about the <tt>Either</tt> type. <tt>Either a b</tt> can be thought of
--   as a 2-tuple <tt>(tag, value)</tt>, where the value of the tag
--   determines the type of the value. In particular, either <tt>tag =
--   Left</tt> and <tt>value :: a</tt> or <tt>tag = Right</tt> and
--   <tt>value :: b</tt>.
--   
--   This package allows you to define your own dependent sum types by
--   using your own "tag" types.
@package dependent-sum
@version 0.2.1.0

module Data.GADT.Show

-- | <a>Show</a>-like class for 1-type-parameter GADTs. <tt>GShow t =&gt;
--   ...</tt> is equivalent to something like <tt>(forall a. Show (t a))
--   =&gt; ...</tt>. The easiest way to create instances would probably be
--   to write (or derive) an <tt>instance Show (T a)</tt>, and then simply
--   say:
--   
--   <pre>
--   instance GShow t where gshowsPrec = showsPrec
--   </pre>
class GShow t
gshowsPrec :: GShow t => Int -> t a -> ShowS
gshows :: GShow t => t a -> ShowS
gshow :: (GShow t) => t a -> String

-- | <tt>GReadS t</tt> is equivalent to <tt>ReadS (forall b. (forall a. t a
--   -&gt; b) -&gt; b)</tt>, which is in turn equivalent to <tt>ReadS
--   (Exists t)</tt> (with <tt>data Exists t where Exists :: t a -&gt;
--   Exists t</tt>)
type GReadS t = String -> [(forall b. (forall a. t a -> b) -> b, String)]

-- | <a>Read</a>-like class for 1-type-parameter GADTs. Unlike
--   <a>GShow</a>, this one cannot be mechanically derived from a
--   <a>Read</a> instance because <a>greadsPrec</a> must choose the phantom
--   type based on the <a>String</a> being parsed.
class GRead t
greadsPrec :: GRead t => Int -> GReadS t
greads :: GRead t => GReadS t
gread :: GRead t => String -> (forall a. t a -> b) -> b

module Data.GADT.Compare

-- | Backwards compatibility alias; as of GHC 7.8, this is the same as
--   `(:~:)`.
type (:=) = (:~:)

-- | A class for type-contexts which contain enough information to (at
--   least in some cases) decide the equality of types occurring within
--   them.
class GEq f

-- | Produce a witness of type-equality, if one exists.
--   
--   A handy idiom for using this would be to pattern-bind in the Maybe
--   monad, eg.:
--   
--   <pre>
--   extract :: GEq tag =&gt; tag a -&gt; DSum tag -&gt; Maybe a
--   extract t1 (t2 :=&gt; x) = do
--       Refl &lt;- geq t1 t2
--       return x
--   </pre>
--   
--   Or in a list comprehension:
--   
--   <pre>
--   extractMany :: GEq tag =&gt; tag a -&gt; [DSum tag] -&gt; [a]
--   extractMany t1 things = [ x | (t2 :=&gt; x) &lt;- things, Refl &lt;- maybeToList (geq t1 t2)]
--   </pre>
--   
--   (Making use of the <tt>DSum</tt> type from <a>Data.Dependent.Sum</a>
--   in both examples)
geq :: GEq f => f a -> f b -> Maybe (a := b)

-- | If <tt>f</tt> has a <a>GEq</a> instance, this function makes a
--   suitable default implementation of '(==)'.
defaultEq :: GEq f => f a -> f b -> Bool

-- | If <tt>f</tt> has a <a>GEq</a> instance, this function makes a
--   suitable default implementation of '(/=)'.
defaultNeq :: GEq f => f a -> f b -> Bool

-- | A type for the result of comparing GADT constructors; the type
--   parameters of the GADT values being compared are included so that in
--   the case where they are equal their parameter types can be unified.
data GOrdering a b
GLT :: GOrdering a b
GEQ :: GOrdering t t
GGT :: GOrdering a b

-- | TODO: Think of a better name
--   
--   This operation forgets the phantom types of a <a>GOrdering</a> value.
weakenOrdering :: GOrdering a b -> Ordering

-- | Type class for orderable GADT-like structures. When 2 things are
--   equal, must return a witness that their parameter types are equal as
--   well (GEQ). |Type class for comparable GADT-like structures. When 2
--   things are equal, must return a witness that their parameter types are
--   equal as well (<a>GEQ</a>).
class GEq f => GCompare f
gcompare :: GCompare f => f a -> f b -> GOrdering a b

-- | Propositional equality. If <tt>a :~: b</tt> is inhabited by some
--   terminating value, then the type <tt>a</tt> is the same as the type
--   <tt>b</tt>. To use this equality in practice, pattern-match on the
--   <tt>a :~: b</tt> to get out the <tt>Refl</tt> constructor; in the body
--   of the pattern-match, the compiler knows that <tt>a ~ b</tt>.
data (:~:) (a :: k) (b :: k) :: k -> k -> *
Refl :: (:~:) k b b
instance Data.GADT.Show.GShow ((Data.GADT.Compare.:=) a)
instance Data.GADT.Show.GRead ((Data.GADT.Compare.:=) a)
instance forall (k :: BOX) (a :: k). Data.GADT.Compare.GEq ((Data.GADT.Compare.:=) a)
instance forall (k :: BOX) (a :: k) (b :: k). GHC.Classes.Eq (Data.GADT.Compare.GOrdering a b)
instance forall (k :: BOX) (a :: k) (b :: k). GHC.Classes.Ord (Data.GADT.Compare.GOrdering a b)
instance forall (k :: BOX) (a :: k) (b :: k). GHC.Show.Show (Data.GADT.Compare.GOrdering a b)
instance Data.GADT.Show.GShow (Data.GADT.Compare.GOrdering a)
instance Data.GADT.Show.GRead (Data.GADT.Compare.GOrdering a)
instance forall (k :: BOX) (a :: k). Data.GADT.Compare.GCompare ((Data.GADT.Compare.:=) a)

module Data.Dependent.Sum

-- | A basic dependent sum type; the first component is a tag that
--   specifies the type of the second; for example, think of a GADT such
--   as:
--   
--   <pre>
--   data Tag a where
--      AString :: Tag String
--      AnInt   :: Tag Int
--   </pre>
--   
--   Then, we have the following valid expressions of type <tt>DSum
--   Tag</tt>:
--   
--   <pre>
--   AString :=&gt; "hello!"
--   AnInt   :=&gt; 42
--   </pre>
--   
--   And we can write functions that consume <tt>DSum Tag</tt> values by
--   matching, such as:
--   
--   <pre>
--   toString :: DSum Tag -&gt; String
--   toString (AString :=&gt; str) = str
--   toString (AnInt   :=&gt; int) = show int
--   </pre>
--   
--   By analogy to the (key =&gt; value) construction for dictionary
--   entries in many dynamic languages, we use (key :=&gt; value) as the
--   constructor for dependent sums. The :=&gt; operator has very low
--   precedence and binds to the right, so if the <tt>Tag</tt> GADT is
--   extended with an additional constructor <tt>Rec :: Tag (DSum
--   Tag)</tt>, then <tt>Rec :=&gt; AnInt :=&gt; 3 + 4</tt> is parsed as
--   would be expected (<tt>Rec :=&gt; (AnInt :=&gt; (3 + 4))</tt>) and has
--   type <tt>DSum Tag</tt>. Its precedence is just above that of <a>$</a>,
--   so <tt>foo bar $ AString :=&gt; "eep"</tt> is equivalent to <tt>foo
--   bar (AString :=&gt; "eep")</tt>.
data DSum tag
(:=>) :: !(tag a) -> a -> DSum tag

-- | In order to make a <a>Show</a> instance for <tt>DSum tag</tt>,
--   <tt>tag</tt> must be able to show itself as well as any value of the
--   tagged type. <a>GShow</a> together with this class provides the
--   interface by which it can do so.
--   
--   <tt>ShowTag tag =&gt; t</tt> is conceptually equivalent to something
--   like this imaginary syntax: <tt>(forall a. Inhabited (tag a) =&gt;
--   Show a) =&gt; t</tt>, where <tt>Inhabited</tt> is an imaginary
--   predicate that characterizes non-empty types, and <tt>a</tt> does not
--   occur free in <tt>t</tt>.
--   
--   The <tt>Tag</tt> example type introduced in the <a>DSum</a> section
--   could be given the following instances:
--   
--   <pre>
--   instance GShow Tag where
--       gshowsPrec _p AString = showString "AString"
--       gshowsPrec _p AnInt   = showString "AnInt"
--   instance ShowTag Tag where
--       showTaggedPrec AString = showsPrec
--       showTaggedPrec AnInt   = showsPrec
--   </pre>
class GShow tag => ShowTag tag

-- | Given a value of type <tt>tag a</tt>, return the <a>showsPrec</a>
--   function for the type parameter <tt>a</tt>.
showTaggedPrec :: ShowTag tag => tag a -> Int -> a -> ShowS
class GRead tag => ReadTag tag
readTaggedPrec :: ReadTag tag => tag a -> Int -> ReadS a

-- | In order to make a <a>Read</a> instance for <tt>DSum tag</tt>,
--   <tt>tag</tt> must be able to parse itself as well as any value of the
--   tagged type. <a>GRead</a> together with this class provides the
--   interface by which it can do so.
--   
--   <tt>ReadTag tag =&gt; t</tt> is conceptually equivalent to something
--   like this imaginary syntax: <tt>(forall a. Inhabited (tag a) =&gt;
--   Read a) =&gt; t</tt>, where <tt>Inhabited</tt> is an imaginary
--   predicate that characterizes non-empty types, and <tt>a</tt> does not
--   occur free in <tt>t</tt>.
--   
--   The <tt>Tag</tt> example type introduced in the <a>DSum</a> section
--   could be given the following instances:
--   
--   <pre>
--   instance GRead Tag where
--       greadsPrec _p str = case tag of
--          "AString"   -&gt; [(\k -&gt; k AString, rest)]
--          "AnInt"     -&gt; [(\k -&gt; k AnInt,   rest)]
--          _           -&gt; []
--          where (tag, rest) = break isSpace str
--   instance ReadTag Tag where
--       readTaggedPrec AString = readsPrec
--       readTaggedPrec AnInt   = readsPrec
--   </pre>

-- | In order to test <tt>DSum tag</tt> for equality, <tt>tag</tt> must
--   know how to test both itself and its tagged values for equality.
--   <a>EqTag</a> defines the interface by which they are expected to do
--   so.
--   
--   Continuing the <tt>Tag</tt> example from the <a>DSum</a> section, we
--   can define:
--   
--   <pre>
--   instance GEq Tag where
--       geq AString AString = Just Refl
--       geq AnInt   AnInt   = Just Refl
--       geq _       _       = Nothing
--   instance EqTag Tag where
--       eqTagged AString AString = (==)
--       eqTagged AnInt   AnInt   = (==)
--   </pre>
--   
--   Note that <a>eqTagged</a> is not called until after the tags have been
--   compared, so it only needs to consider the cases where <a>gcompare</a>
--   returns <a>GEQ</a>.
class GEq tag => EqTag tag

-- | Given two values of type <tt>tag a</tt> (for which <a>gcompare</a>
--   returns <a>GEQ</a>), return the <a>==</a> function for the type
--   <tt>a</tt>.
eqTagged :: EqTag tag => tag a -> tag a -> a -> a -> Bool

-- | In order to compare <tt>DSum tag</tt> values, <tt>tag</tt> must know
--   how to compare both itself and its tagged values. <a>OrdTag</a>
--   defines the interface by which they are expected to do so.
--   
--   Continuing the <tt>Tag</tt> example from the <a>EqTag</a> section, we
--   can define:
--   
--   <pre>
--   instance GCompare Tag where
--       gcompare AString AString = GEQ
--       gcompare AString AnInt   = GLT
--       gcompare AnInt   AString = GGT
--       gcompare AnInt   AnInt   = GEQ
--   instance OrdTag Tag where
--       compareTagged AString AString = compare
--       compareTagged AnInt   AnInt   = compare
--   </pre>
--   
--   As with <a>eqTagged</a>, <a>compareTagged</a> only needs to consider
--   cases where <a>gcompare</a> returns <a>GEQ</a>.
class (EqTag tag, GCompare tag) => OrdTag tag

-- | Given two values of type <tt>tag a</tt> (for which <a>gcompare</a>
--   returns <a>GEQ</a>), return the <a>compare</a> function for the type
--   <tt>a</tt>.
compareTagged :: OrdTag tag => tag a -> tag a -> a -> a -> Ordering
instance GHC.Show.Show a => Data.Dependent.Sum.ShowTag ((Data.GADT.Compare.:=) a)
instance GHC.Show.Show a => Data.Dependent.Sum.ShowTag (Data.GADT.Compare.GOrdering a)
instance Data.Dependent.Sum.ShowTag tag => GHC.Show.Show (Data.Dependent.Sum.DSum tag)
instance GHC.Read.Read a => Data.Dependent.Sum.ReadTag ((Data.GADT.Compare.:=) a)
instance Data.Dependent.Sum.ReadTag tag => GHC.Read.Read (Data.Dependent.Sum.DSum tag)
instance GHC.Classes.Eq a => Data.Dependent.Sum.EqTag ((Data.GADT.Compare.:=) a)
instance Data.Dependent.Sum.EqTag tag => GHC.Classes.Eq (Data.Dependent.Sum.DSum tag)
instance GHC.Classes.Ord a => Data.Dependent.Sum.OrdTag ((Data.GADT.Compare.:=) a)
instance Data.Dependent.Sum.OrdTag tag => GHC.Classes.Ord (Data.Dependent.Sum.DSum tag)
