Расширьте синтаксический анализатор, чтобы построить квази-квотер для паттернов
Я хотел бы построить квазиквотер для создания шаблонов, которые соответствуют поддеревьям в Java AST, так что вместо BasicFor (Just (ForInitExps init)) (Just cond) (Just inc) body
Я могу написать что-то вроде [java|for (#init ; #cond ; #inc) #body|]
, Наивным подходом было бы модифицировать каждое правило Parsec в парсере language-java, например:
catch :: P Catch
catch = do
tok KW_Catch
fp <- parens formalParam
b <- block
return $ Catch fp b
становится
catchP :: P TH.Pat
catchP = bindP <|> do
tok KW_Catch
fp <- parens formalParam
b <- block
return $ ConP "Catch" [fp, b]
Где я 1. изменить тип подписи, чтобы произвести TH.Pat
; 2. добавить альтернативу bindP
для анализа мета-переменных (например, #init
упомянутое выше); 3. изменить выражение возврата в TH.Pat
вместо Catch
, Я должен был бы сделать это для каждого отдельного правила parsec, которое является довольно много стандартного кода. Есть ли способ отказаться от таких шаблонов? Возможно, используя монаду ParsecT или взломать сам парсек?