using types and values Values match the types, usage of values type-checked Users can statically derive values via types Justin Woo Type classes: pattern matching for types October 18 2018 2 / 23
| Nothing Key parts: data: begins the data type declaration Maybe: the name of our data type a: a parameter of our data type Just: A constructor of Maybe |: Separates constructors in our type For a given data type, there are one or more constructors. Justin Woo Type classes: pattern matching for types October 18 2018 3 / 23
be used to create values of our data type: data Maybe a = Just a | Nothing mkJust :: forall a. a -> Maybe a mkJust = Just mkNothing :: forall a. Maybe a mkNothing = Nothing Justin Woo Type classes: pattern matching for types October 18 2018 4 / 23
of data types, but how do we then match on constructors of data types? Using case expressions: isJust :: forall a. Maybe a -> Boolean isJust m = case m of Just x -> true Nothing -> false At definition sites: isJust' :: forall a. Maybe a -> Boolean isJust' (Just x) = true isJust' Nothing = false Justin Woo Type classes: pattern matching for types October 18 2018 5 / 23
commonly useful data types have multiple constructors* Sum members can be pattern matched for *i.e. they are Sum types Justin Woo Type classes: pattern matching for types October 18 2018 6 / 23
to work with the type level: 1 What are type classes? 2 What are instances? 3 What are kinds? 4 What are proxies? Justin Woo Type classes: pattern matching for types October 18 2018 7 / 23
to match on types based on kinds, allowing for defining methods for types which have an instance of a given class class Show a where show :: a -> String Justin Woo Type classes: pattern matching for types October 18 2018 8 / 23
a class for a matched type by an instance head instance showString :: Show String where show s = s myString :: String myString = show "value" Justin Woo Type classes: pattern matching for types October 18 2018 9 / 23
of which the most common is Type and has associated runtime values. foreign import data ForeignData :: Type foreign import kind MaybeTy foreign import data JustTy :: Type -> MaybeTy foreign import data NothingTy :: MaybeTy Justin Woo Type classes: pattern matching for types October 18 2018 10 / 23
that has a parameter of a given kind, where the parameter is not exposed as a value. -- no kind signature: inferred as Type data Proxy ty = Proxy data Proxy2 (ty :: Type) = Proxy2 data MaybeTyProxy (mt :: MaybeTy) = MaybeTyProxy justIntProxy :: MaybeTyProxy (JustTy Int) justIntProxy = MaybeTyProxy Justin Woo Type classes: pattern matching for types October 18 2018 11 / 23
can see the correspondence: values : Types :: types : kinds case of : class branch : instance Justin Woo Type classes: pattern matching for types October 18 2018 12 / 23
type level? We can use multi-param type classes, along with functional dependencies (“fundeps”): class IsJustTy (mt :: MaybeTy) (result :: Type.Data.Boolean) | mt -> result instance justTypeIsJustTy :: IsJustTy (JustTy a) Type.Data.True instance nothingTypeIsJustTy :: IsJustTy NothingTy Type.Data.False The parameter mt determines result, i.e. instances can be matched for by mt alone. Justin Woo Type classes: pattern matching for types October 18 2018 14 / 23
If anything, the parallel is closer with an open polymorphic variant. Instances are “partial” Compilation fails when instances cannot be found with No type class instance was found for _. There are some limited ways of doing wildcard matches for type classes e.g. using instance chains (groups) in PureScript 0.12 to constrain instances to a module in a continuous group. Justin Woo Type classes: pattern matching for types October 18 2018 16 / 23
be able to derive information and/or values from static information. Computers should do work for us, not the other way around. Runtime checks for static information leave much to be desired Leaving calculations to the runtime that should be verified in compile time leaves us with dead code paths at best. And really, is there actually a difference between an incorrect program and crashes and an incorrect program that “never crashes” but always ends up in an invalid path? Why shouldn’t we actually program using type information? Why should we use types only to check some usages of values rather than reduce error-prone work and more powerfully extract values from static information? Justin Woo Type classes: pattern matching for types October 18 2018 17 / 23
that should be derived from the type information: type DecodeResult a = Either DecodeError a type MyRecord = { apple :: String, banana :: Int } readMyRecord1 :: Foreign -> DecodeResult MyRecord readMyRecord1 f = do apple <- readString =<< readProperty "apple" banana <- readInt =<< readProperty "apple" pure { apple, banana } Justin Woo Type classes: pattern matching for types October 18 2018 18 / 23
at the given field with the correct label and type, why even deal with this? Use Simple-JSON github.com/justinwoo/purescript-simple-json type MyJSON = { apple :: String , banana :: Int , cherry :: Maybe Boolean } decodeToMyJSON :: String -> SimpleJSON.E MyJSON decodeToMyJSON = SimpleJSON.readJSON This is also flexible for inferred field type changing, field addition/removal, etc. Justin Woo Type classes: pattern matching for types October 18 2018 20 / 23
If we have a static parameterized SQLite query, we should be able to build up the request query type: getEm :: forall a b. AllowedParamType a => AllowedParamType b => DBConnection -> { "$name" :: a, "$count" :: b } -> Aff Foreign getEm db = J.queryDB db $ SProxy :: SProxy """ select name, count from mytable where name = $name and count = $count """ Justin Woo Type classes: pattern matching for types October 18 2018 21 / 23
of a Type and type classes of types of a kind. The parallel is not a perfect correspondence, which also sometimes helps us more easily use type information to derive routines and values from types. We can avoid error-prone (non-)boilerplate and use type classes to allow us to take advantage of dependent-typed techniques with PureScript. You don’t have to rely on code generation or the whims of thoughtleaders to make things work the way you see fit! Justin Woo Type classes: pattern matching for types October 18 2018 23 / 23