úÎ9=5´"      !portable experimentalEdward Kmett <ekmett@gmail.com> Safe-Infered p a w replaces the free variable a with p in w ZIf a term has no free variables, you can freely change the type of free variables it uses portable experimentalEdward Kmett <ekmett@gmail.com> Safe-Infered1Instantces may or may not be monad transformers. If they are, then you can use m >>>= f = m >>= lift . f CThis is useful for types like expression lists, case alternatives, I schemas, etc. that may not be expressions in their own right, but often  contain one. portable experimentalEdward Kmett <ekmett@gmail.com> Safe-Infered"I am not a number, I am a  free monad!" Var b a) represents variables that may either be bound (B) or free (F) FIt is also technically a free monad in the same near trivial sense as " #$%&'()*+,-./012#$%&'()*+,-./012portable experimentalEdward Kmett <ekmett@gmail.com> Safe-Infered   b f a is an f$ expression with bound variables in b, and free variables in a HWe store bound variables as their generalized de Bruijn representation,  in that we're allowed to 3 (using =) an entire tree rather than only succ individual variables,  but we'(re still only allowed to do so once per  . Weakening trees permits O(1) weakening O permits more sharing opportunities. Here the deBruijn 0 is represented by the  constructor of  , while the de Bruijn 49 (which may be applied to an entire tree!) is handled by . 6NB: equality and comparison quotient out the distinct  placements allowed by ` the generalized de Bruijn representation and return the same result as a traditional de Bruijn  representation would. ELogically you can think of this as if the shape were the traditional  f (Var b a), but the extra  'f a' inside permits us a cheaper 3. 8Capture some free variables in an expression to yield a   with bound variables in b  Abstract over a single variable 1Enter a scope, instantiating all bound variables Enter a  + that binds one variable, instantiating it * quotients out the possible placements of  in   H by distributing them all to the leaves. This yields a more traditional 0 de Bruijn indexing scheme for bound variables.   fromScope . toScope = id - fromScope . toScope . fromScope = fromScope ( . ) is idempotent ;Perform substitution on both bound and free variables in a   1Perform a change of variables on bound variables JPerform a change of variables, reassigning both bound and free variables. >Perform a change of variables on bound variables given only a 5 instance  A version of ) that can be used when you only have the 5 instance MObtain a result by collecting information from both bound and free variables MObtain a result by collecting information from both bound and free variables -mapM_ over the variables bound by this scope 6SThe monad permits substitution on free variables, while preserving bound variables 78< is provides a list (with duplicates) of the free variables '  !9:;<=>?@AB6C7D  !  !%   !9:;<=>?@AB6C7Dportable experimentalEdward Kmett <ekmett@gmail.com> Safe-Infered!  !!  !E      !"#$%&'()*+,-./0123456789:;&<=&>?@A&BCDEFGHIJKLMNOP bound-0.2 Bound.Term Bound.Class Bound.Var Bound.ScopeBound substituteclosedisClosed>>>==<<<VarFBScopeunscopeabstract abstract1 instantiate instantiate1 fromScopetoScopesplatbindingsmapBoundmapScope liftMBound liftMScope foldMapBound foldMapScopetraverseBound_traverseScope_ mapMBound_ mapMScope_ traverseBound traverseScope mapMBound mapMScopebase Data.EitherEither $fRead1Var $fShow1Var $fOrd1Var$fEq1Var $fRead2Var $fShow2Var $fOrd2Var$fEq2Var$fBitraversableVar$fBifoldableVar$fBifunctorVar $fMonadVar$fApplicativeVar$fTraversableVar $fFoldableVar $fFunctorVartransformers-0.3.0.0Control.Monad.Trans.ClassliftGHC.EnumsuccGHC.BaseMonad $fMonadScope$fFoldableScope Data.FoldabletoList $fBoundScope $fRead1Scope $fReadScope $fShow1Scope $fShowScope $fOrd1Scope $fOrdScope $fEq1Scope $fEqScope$fMonadTransScope$fTraversableScope$fFunctorScope