Reputation: 23
I defined Symbol
data type that can be either BuiltInTypeSymbol
or ProcedureSymbol
. ProcedureSymbol
may have a parent of type Scope
. So I added Scope
type constraint for ProcedureSymbol
data constructor and parent
function.
data Symbol where
BuiltInTypeSymbol :: String -> Symbol
ProcedureSymbol :: Scope sc => String -> sc -> [Symbol] -> Symbol
name :: Symbol -> String
name (BuiltInTypeSymbol n) = n
name (ProcedureSymbol n _ _) = n
parent :: Scope sc => Symbol -> Maybe sc
parent (ProcedureSymbol _ par _) = Just par
parent _ = Nothing
class Scope s where
getName :: s -> String
getEnclosingScope :: Scope sc => s -> Maybe sc
define :: s -> Symbol -> s
resolve :: s -> String -> Maybe Symbol
When I try to compile this code I got the following compile error:
SymbolTable.hs:13:36: error: * Couldn't match type `sc1' with `sc' `sc1' is a rigid type variable bound by a pattern with constructor: ProcedureSymbol :: forall sc. Scope sc => String -> sc -> [Symbol] -> Symbol, in an equation for `parent' at SymbolTable.hs:13:9 `sc' is a rigid type variable bound by the type signature for: parent :: forall sc. Scope sc => Symbol -> Maybe sc at SymbolTable.hs:12:11 Expected type: Maybe sc Actual type: Maybe sc1 * In the expression: Just par In an equation for `parent': parent (ProcedureSymbol _ par _) = Just par * Relevant bindings include par :: sc1 (bound at SymbolTable.hs:13:27) parent :: Symbol -> Maybe sc (bound at SymbolTable.hs:13:1)
How can I make this code compile?
Upvotes: 2
Views: 1130
Reputation: 16224
As @David Young pointed, you can add a type parameter to your Symbol constructor, like this:
{-# LANGUAGE GADTs #-}
data Symbol a where
BuiltInTypeSymbol :: String -> Symbol a
ProcedureSymbol :: Scope a => String -> a -> [Symbol a] -> Symbol a
class Scope s where
getName :: s -> String
getEnclosingScope :: Scope sc => s -> Maybe sc
define :: s -> Symbol s-> s
resolve :: s -> String -> Maybe (Symbol s)
name :: Symbol a -> String
name (BuiltInTypeSymbol n) = n
name (ProcedureSymbol n _ _) = n
parent :: Scope sc => Symbol sc -> Maybe sc
parent (ProcedureSymbol _ par _) = Just par
parent _ = Nothing
Upvotes: 0