hint icon indicating copy to clipboard operation
hint copied to clipboard

bind a outside value to an interpreted variable

Open gelisam opened this issue 4 years ago • 0 comments

It is easy to move those values from the interpreter to the enclosing program using interpret. But what about moving values from the enclosing program to the interpreter?

If we are only interested in interpreting a single expression which refers to one or more outside values, there are currently two solutions:

  1. if the value has a Show instance, we can interpret that String representation.
  2. if the value has a Typeable instance, we can interpret a function, and then pass our value to the function.

Now that we have runStmt, we can also give a name to a value so that it is available in future expressions. This time, there is only one solution:

  1. if the value has a Show instance, we can run a statement of the form var <- expr using that String representation.

It would be nice to complete the picture using a solution for Typeable instances. I figured out how to implement that solution using the existing primitives, and I think the trick is sufficiently non-obvious that it's worth including in the library:

-- Bind a variable inside the interpreter to a value from outside the
-- interpreter.
bind :: forall a. Typeable a => String -> a -> M ()
bind var value = do
  liftHint $ Hint.runStmt
               ( "tmpIORef <- newIORef (undefined :: "
              ++ show (typeOf (undefined :: a))
              ++ ")"
               )
  tmpIORef <- liftHint
            $ Hint.interpret
                "tmpIORef"
                (Hint.as :: IORef a)
  liftIO $ writeIORef tmpIORef value
  liftHint $ Hint.runStmt (var ++ " <- readIORef tmpIORef")

gelisam avatar Mar 03 '21 22:03 gelisam