Changelog for unbound-generics-0.4.0
NEXT
0.4.0
-
New binding specification type
Ignore
.Any two
Ignore T
terms will always be alpha-equivalent to each other, will be considered to contain no variables, and will not have any substitution apply beneathIgnore
. Useful for attaching annotation terms to your AST.import Text.Parsec.Pos (SourcePos) data Expr = ... | Lambda (Ignore SourcePos) (Bind (Name Expr) Expr)
As expected, any two
Lambda
expressions will be considered alpha-equivalent even if they differ in source position.Note that the
Ignore
will block operations onName a
for alla
, which can be a little unexpected:data Ty = TyVar (Name Ty) | TyArr Ty Ty instance Subst Ty Ty where ... data Expr = ... | Var (Name Expr) | Lambda (Ignore Ty) (Bind (Name Expr) Expr) instance Subst Ty Expr
Applying a substitution of a type for a free type variable to a
Lambda
will not descend into theIgnore Ty
.Thanks Reed Mullanix (TOTWBF) for the new operation.
-
Fix an issue in substitution where traversal would not continue in an AST node for which
isvar
orisCoerceVar
is defined to return non-Nothing
but which had additional structure.For example, in a language with meta variables and explicit substitutions:
data Expr = ... -- normal variables that stand for expressions | Var (Name Expr) -- a meta variable occurrence and an explicit substitution -- of expressions to substitute in for the free variables | MetaVar (Name Meta) [(Name Expr, Expr)] -- a meta variable stands for an expression with some free term vars data Meta = MetaVar Expr -- substitution for a meta in an expression instance Subst Expr Meta where isCoerceVar (MetaVar u sub) = Just (SubstCoerce u (Just . applyExplicitSubst sub)) applyExplicitSubst :: [(Name Expr, Expr)] -> Meta -> Expr applyExplicitSubst s (MetaVar e) = substs s e
Given an expression
e1
defined asMetaVar "u" [("x", 10)]
, we may want to substitute aMeta ("x" + "x")
for"u"
to get10 + 10
(that is, we replace"u"
by the expression"x" + "x"
and immediately apply the substitution10
for"x"
).Now suppose we have an expression
e2
defined asMetaVar "v" [("y", e1)]
(that is, an occurrence of meta var "v" together with a substitution ofe1
from above for"y"
). If we again try to substituteMeta ("x" + "x")
for"u"
ine2
, we would expect to getMetaVar "v" [("y", 10 + 10)]
(that is, since "v" is not equal to "u", we leave the meta var alone, but substitute for any occurrences of "u" in the explicit substitution, soe1
becomes10 + 10
as before).The bug in previous versions of
unbound-generics
was that we would incorrectly leaveMetaVar "v" [("y", e1)]
unchanged as soon as we saw thatisCoerceVar (MetaVar "v" [("y", e1)])
returnedJust (SubstCoerce "u" ...)
where"u" /= "v"
.Thanks Reed Mullanix (TOTWBF) for finding and fixing this issue. https://github.com/lambdageek/unbound-generics/issues/26
0.3.4
- Bump
containers
upper bound to support0.6
. (GHC 8.6.1 support) Thanks Christiaan Baaij.
0.3.3
- Bump
exceptions
upper bound to support0.10.0
0.3.2
- Bump
deepseq >= 1.4.0.0
remove benchmark dependency ondeepseq-generics
- Tested with GHC 8.4.1
- Tested with GHC 8.2.2
- Compile with
-Wcompat
- Add
Semigroup
instances for all types that were previouslyMonoid
instances - Added more examples to the examples/ directory
- Added "exceptions" dependency and
MonadThrow
,MonadCatch
,MonadMask
instances forFreshMT
andLFreshMT
. Thanks Alex McKenna.
0.3.1
- Tested with GHC 8.0.1
- Removed
Generic b
constraint fromSubst b (Name a)
instance.
0.3
- Change types of
open
andclose
to takeNthPatFind
andNamePatFind
instead of generic patterns, update call sites. - Add newtype wrappers and Monoid instances for
NthPatFind
andNamePatFind
- Change
isTerm
to returnAll
instead ofBool
0.2
-
Incorporating some of the extras/oversights from clash-lib Unbound.Generics.LocallyNameless.Extra
- Make
Embed
an instance ofOrd
NFData
instances (see below)
- Make
-
Re-implement
freshen'
andgfreshen
using a free monad to give GHC a chance to inline it all away. This changes the type ofgfreshen
. Major version bump.- Expose
FFM
,liftFFM
andretractFFM
- Expose
-
Provide
NFData
instances for all the combinators. Depend on 'deepseq' -
Start benchmarking some of the operations (particularly
unbind
).
0.1.2.1
- Fix ghc-7.10 build.
- Haddock cleanup.
0.1.2
-
Added
IsEmbed
typeclass- Depend on 'profunctors'
-
Changed
embed
andunembed
to work over anyIsEmbed
type. -
Added
Shift
type for shifting the scope of embedded terms out one level.
0.1.1
- Added
isNullDisjointSet
function. - Implement a TH
makeClosedAlpha
splice for constructing trivial leaf instances.
0.1
-
Add
acompare
functiona andacompare'
method toAlpha
typeclass. (christiaanb)Handwritten
Alpha
instances will need to define this additional method now. Major version bump.
0.0.3
-
Add 'name2Integer' method (christiaanb)
-
Export internal type-directed
gaeq
,gopen
,gclose
, etc functions fromUnbound.Generics.LocallyNameless.Alpha
.Allows definitions like:
instance Alpha Term where aeq' _ (Prim t1 _dk1) (Prim t2 _dk2) = t1 == t2 aeq' c t1 t2 = gaeq c (from t1) (from t2)
0.0.2.1
- Unconditionally add ErrorT and ExceptT instances using transformers-compat (bergmark)
0.0.2
-
Add 'Rec' pattern and 'TRec' term combinators.
-
Alpha instance for '()'
0.0.1
-
Add 'lunbind2' function.
-
Doc updates.
-
Switch from 'HUnit' to 'Tasty' for testing.
0.0.0.90
- Initial (re-)implementation effort.