diff options
Diffstat (limited to 'testsuite/tests/generics/GFullyStrict.hs')
-rw-r--r-- | testsuite/tests/generics/GFullyStrict.hs | 57 |
1 files changed, 57 insertions, 0 deletions
diff --git a/testsuite/tests/generics/GFullyStrict.hs b/testsuite/tests/generics/GFullyStrict.hs new file mode 100644 index 0000000000..7c879d9877 --- /dev/null +++ b/testsuite/tests/generics/GFullyStrict.hs @@ -0,0 +1,57 @@ +{-# LANGUAGE DefaultSignatures #-} +{-# LANGUAGE DeriveAnyClass #-} +{-# LANGUAGE DeriveGeneric #-} +{-# LANGUAGE FlexibleContexts #-} +{-# LANGUAGE FlexibleInstances #-} +{-# LANGUAGE ScopedTypeVariables #-} +{-# LANGUAGE TypeOperators #-} +module Main where + +import Data.Proxy (Proxy(..)) +import GHC.Generics + +main :: IO () +main = do + print (fullyStrict (Proxy :: Proxy (StrictMaybe Bool))) + print (fullyStrict (Proxy :: Proxy (Maybe Bool))) + +data StrictMaybe a = StrictNothing | StrictJust !a + deriving (FullyStrict, Generic) + +instance FullyStrict Bool +instance FullyStrict a => FullyStrict (Maybe a) + +class FullyStrict a where + fullyStrict :: proxy a -> Bool + default fullyStrict :: (GFullyStrict (Rep a)) => proxy a -> Bool + fullyStrict _ = gfullyStrict (Proxy :: Proxy (Rep a p)) + +class GFullyStrict f where + gfullyStrict :: proxy (f p) -> Bool + +instance GFullyStrict V1 where + gfullyStrict _ = True + +instance GFullyStrict U1 where + gfullyStrict _ = True + +instance FullyStrict c => GFullyStrict (Rec0 c) where + gfullyStrict _ = fullyStrict (Proxy :: Proxy c) + +instance GFullyStrict f => GFullyStrict (D1 c f) where + gfullyStrict _ = gfullyStrict (Proxy :: Proxy (f p)) + +instance GFullyStrict f => GFullyStrict (C1 c f) where + gfullyStrict _ = gfullyStrict (Proxy :: Proxy (f p)) + +instance (GFullyStrict f, Selector c) => GFullyStrict (S1 c f) where + gfullyStrict _ = gfullyStrict (Proxy :: Proxy (f p)) + && selDecidedStrictness (undefined :: S1 c f p) /= DecidedLazy + +instance (GFullyStrict f, GFullyStrict g) => GFullyStrict (f :+: g) where + gfullyStrict _ = + gfullyStrict (Proxy :: Proxy (f p)) && gfullyStrict (Proxy :: Proxy (g p)) + +instance (GFullyStrict f, GFullyStrict g) => GFullyStrict (f :*: g) where + gfullyStrict _ = + gfullyStrict (Proxy :: Proxy (f p)) && gfullyStrict (Proxy :: Proxy (g p)) |