Я использую библиотеку syntactic для создания АСТ. Для того, чтобы оценить AST до значения (Haskell), все мои узлы должны быть экземпляром синтаксической класса EvalEnv
:Как отменить мой шаблон
class EvalEnv sym env where
compileSym :: proxy env -> sym sig -> DenotationM (Reader env) sig
синтаксический также предоставляет «по умолчанию» реализация:
compileSymDefault :: (Eval sym, Signature sig)
=> proxy env -> sym sig -> DenotationM (Reader env) sig
но ограничение на sig
недостижим в случаях EvalEnv
, делая следующее (скажем, дублирующих друг друга) экземпляра невозможно:
instance EvalEnv sym env where
compileSym = compileSymDefault
Все мои пользовательские AST узлы GADTs, как правило, с несколькими конструкторами, где a
параметр всегда удовлетворяет ограничение для compileSymDefault
:
data ADDITIVE a where
Add :: (Num a) => ADDITIVE (a :-> a :-> Full a)
Sub :: (Num a) => ADDITIVE (a :-> a :-> Full a)
В результате, я обнаружил, что все моих экземпляров для EvalEnv
взгляда как:
instance EvalEnv ADDITIVE env where
compileSym p Add = compileSymDefault p Add
compileSym p Sub = compileSymDefault p Sub
Этот шаблонный экземпляр идентичен для всех узлов AST, и каждый из GADT конструкторов должен быть перечислен отдельно, так как конструктор подпись GADT предполагает compileSymDefault
Ограничения.
Есть ли способ избежать необходимости перечислять каждый конструктор для каждого типа узла, который я делаю?
Несвязанный, я не уверен, что вы должны передавать прокси-сервер для 'compileSym'. Это необязательно и усложняет это определение. – Carl
@Carl Если было не ясно, 'compileSymDefault' предоставляется синтаксической библиотекой. Там может быть какая-то причина. – crockeea
Где находится класс 'Additive'? Я не могу найти его ни в одном из «синтаксических» модулей, и ни один из них не может быть Hayoo. http://hayoo.fh-wedel.de/?query=syntactic+Additive – Cirdec