1 Replies - 473 Views - Last Post: 16 October 2016 - 03:59 PM

#1 NoYouDidnt  Icon User is offline

  • D.I.C Head

Reputation: 5
  • View blog
  • Posts: 55
  • Joined: 04-July 15

Saving variables in a small Haskell language

Posted 16 October 2016 - 02:05 PM

Trying to write a small language in Haskell

This is the data type that I'm using

data Ast = Number Integer | Name String | App Ast [Ast] | Block [Ast] | Case Ast [Ast] | Bool Ast Ast Ast | Default | Set String Ast  | Lambda String Ast
    deriving (Eq, Show, Ord)

I have a parser that will convert an input like "set a 5; set b (a, 7)+;" to this

Block [Set "a" Number 5, Set "b" (App (Name "+") [Name "a", Number 7])]

To be able to use the value associated with the variable "a" when evaluating the second Set, I need to store the data in "Memory". I am supposed to use use these to manage it:

type Memory = (Integer, Integer -> Maybe Ast)

newtype Context = Context (String -> Maybe Integer)
instance Show Context where 
    show _ = ""

In Memory, the first value of the tuple is the next free address in memory, and the second a function that will eventually return the Ast if it is in Memory.

The Context is mapping the variable name to the address in Memory.

I have these helper functions
lookupMem :: Memory -> Integer -> Maybe Ast
lookupMem (_, f) x = f x   

emptyMem :: Memory
emptyMem = (0, \ _ -> Nothing)

lookupCtx :: Context -> String -> Maybe Integer
lookupCtx (Context f) v = f v

emptyCtx :: Context
emptyCtx = Context (const Nothing)  

addToMem :: Memory -> Ast -> (Integer, Memory)    
addToMem (adr, b ) ast = (adr, (succ adr, function))
    where function = \y -> case (==adr) of True -> Just ast _ -> b y

addToCtx :: Context -> String -> Integer -> Context
addToCtx (Context f) v x = Context (\y -> case (==v) of True -> Just x _ -> f y)

The "addTo" functions are just pseudo code at this point. I guess I can't write them like that.

However, the part where I am really stuck is the logic when I am evaluating the block. The ctx mem variables contain the emptyMem and emptyCtx when the evaluation starts.

This is what I have at the moment:

eval :: Ast -> Context -> Memory -> (Ast, Context, Memory)

--Evaluate the first expression and proceed with the updated memory/context 

eval (Block (ast : rest)) ctx mem = let (a, uc, um) = eval ast ctx mem in eval (Block rest) uc um

-- First evaluate the var and do some inserting? im not sure

eval (Set var exp) (Context ctx) mem = 
    let (a, uc, um) = eval (Name var) ctx mem -- stuck

-- Need to look up the var and see if there is any value associated with it, and if not, well im not sure.

eval (Name var) (Context ctx) mem = 
    case ctx var of
        Nothing -> 
        Just r ->

eval App ... and so on (these will not have to manage the memory/context)

I wondered if someone can help me, espesically with the eval logic

Is This A Good Question/Topic? 0
  • +

Replies To: Saving variables in a small Haskell language

#2 sepp2k  Icon User is offline

  • D.I.C Lover
  • member icon

Reputation: 2507
  • View blog
  • Posts: 3,961
  • Joined: 21-June 11

Re: Saving variables in a small Haskell language

Posted 16 October 2016 - 03:59 PM

For Set you should look up the memory location associated with the name (no need to evaluate the name), evaluate the expression1 and then return a memory where the looked up address points to the evaluated expression. What AST you should return depends on what the assignment operation is supposed to return in your language. In some languages it returns the assigned value, in other nothing (which would be Default in your representation, I assume).

1 That's assuming your language is supposed to have eager evaluation semantics. Otherwise you'll need to store the expression unevaluated.
Was This Post Helpful? 1
  • +
  • -

Page 1 of 1