11{-# LANGUAGE DerivingVia #-}
2+ {-# LANGUAGE ExistentialQuantification #-}
23{-# LANGUAGE GeneralizedNewtypeDeriving #-}
34{-# LANGUAGE LinearTypes #-}
45{-# LANGUAGE NoImplicitPrelude #-}
@@ -12,6 +13,7 @@ module Data.Semigroup.Linear
1213 ( Semigroup (.. )
1314 , Monoid (.. )
1415 , LEndo (.. ), appLEndo
16+ , Top , throw
1517 , module Data.Semigroup
1618 )
1719 where
@@ -29,7 +31,8 @@ class (Semigroup a, Prelude.Monoid a) => Monoid a where
2931 {-# MINIMAL #-}
3032 mempty :: a
3133 mempty = mempty
32- -- convenience redefine
34+ -- convenience redefine, so that nonlinear Data.Semigroup doesn't have
35+ -- to be imported to use mempty
3336
3437---------------
3538-- Instances --
@@ -38,6 +41,7 @@ class (Semigroup a, Prelude.Monoid a) => Monoid a where
3841instance Semigroup () where
3942 () <> () = ()
4043
44+ -- | The type of linear endomorphisms.
4145newtype LEndo a = LEndo (a ->. a )
4246
4347-- TODO: have this as a newtype deconstructor once the right type can be
@@ -80,3 +84,23 @@ deriving via LWrap All instance Semigroup All
8084deriving via LWrap All instance Monoid All
8185deriving via LWrap Any instance Semigroup Any
8286deriving via LWrap Any instance Monoid Any
87+
88+ -- | `Top` can be thought of as a 'wastebasket' of resources, which any
89+ -- value can be thrown into. On the other hand, it cannot be linearly
90+ -- destroyed, unless into another `Top`.
91+ -- In particular, it has the property that forall x. x ->. Top is inhabited
92+ -- (uniquely), as witnessed by `throw`.
93+ data Top = forall x . Top x
94+
95+ instance Prelude. Semigroup Top where
96+ Top x <> Top y = Top (x,y)
97+ instance Semigroup Top where
98+ Top x <> Top y = Top (x,y)
99+ instance Prelude. Monoid Top where
100+ mempty = Top ()
101+ instance Monoid Top where
102+
103+ -- Export this instead of the constructor so we have the freedom to change
104+ -- the implementation (to the universal encoding, for instance)
105+ throw :: a ->. Top
106+ throw = Top
0 commit comments