@@ -29,6 +29,7 @@ Here is our mid-section datatype
2929> import Data.Char
3030> import Data.List
3131> import Data.Maybe (fromMaybe )
32+ > import Data.Traversable (traverse )
3233
3334> import Control.Monad.Writer
3435
@@ -298,39 +299,36 @@ Translate the rules from string to name-based.
298299> rules2 <- mapM transRule rules1
299300
300301> let
301- > fixType :: (String , [(String ,String )]) -> M (Array Int (Maybe String ) -> String -> String )
302- > fixType (ty,env) = go ty $ const id
302+ > -- tys :: Array Int (M (Maybe (String -> String)))
303+ > tys = accumArray (\ _ x -> x) (return Nothing ) (0 , last_t) $
304+ > [ (nm, liftM Just $ fixType ty env) | (nm,_,Just (ty, env)) <- rules1 ] ++
305+ > [ (nm, return . Just . str . getTokenType $ dirs) | nm <- terminal_names ] -- XXX: Doesn't handle $$ in token
306+ >
307+ > -- fixType :: String -> Subst -> M (String -> String)
308+ > fixType ty env = go ty id
303309> where
304310> isIdent c = isAlphaNum c || c == ' _'
305- > go [] f = return f
306- > go r@ (c: _) f | isLower c = -- an identifier starting with a lower case letter
311+ > go [] s = return s
312+ > go r@ (c: _) s | isLower c = -- an identifier starting with a lower case letter
307313> let (cs,r1) = span isIdent r
308314> in case lookup cs env of -- try to map formal to actual
309315> Nothing -> -- no formal found
310- > go r1 $ \ tys -> f tys . str cs -- do not expand
316+ > go r1 $ s . str cs -- do not expand
311317> Just a -> do -- found actual
312318> nm <- mapToName a
313- > go r1 $ \ tys ->
314- > let t = fromMaybe cs (tys ! nm)
315- > in f tys . brack t
319+ > ty' <- tys ! nm
320+ > go r1 $ s . brack' (fromMaybe (str cs) ty')
316321> | isIdent c = -- an identifier not starting with a lower case letter
317322> let (cs,r1) = span isIdent r
318- > in go r1 $ \ tys -> f tys . str cs -- do not expand
323+ > in go r1 $ s . str cs -- do not expand
319324> | otherwise = -- not an identifier
320325> let (cs,r1) = break isIdent r
321- > in go r1 $ \ tys -> f tys . str cs -- do not expand
322- > mapSndM :: Monad m => (a -> m b ) -> (c , a ) -> m (c , b )
323- > mapSndM f (c, a) = f a >>= \ b -> return (c, b)
326+ > in go r1 $ s . str cs -- do not expand
324327> -- in
325328
326- > tys <- ( mapM . mapSndM) fixType [ (nm,ty) | (nm,_, Just ty) <- rules1 ]
329+ > type_array <- traverse (( fmap . fmap ) ( $ " " )) tys
327330
328331> let
329- > type_array :: Array Int (Maybe String )
330- > type_array = accumArray (\ _ x -> x) Nothing (0 , last_t) $
331- > [ (nm, Just (f type_array " " )) | (nm, f) <- tys ] ++ -- tied a knot!
332- > [ (nm, Just (getTokenType dirs)) | nm <- terminal_names ] -- XXX: Doesn't handle $$ in token
333- >
334332> env_array :: Array Int String
335333> env_array = array (errorTok, last_t) name_env
336334> -- in
0 commit comments