微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何使用HughesPJ的漂亮打印库正确缩进块?

如何解决如何使用HughesPJ的漂亮打印库正确缩进块?

我有以下编程语言语法:

data Expr = ...

data Stmt = SExpr Expr | SBlock Block | SLet Fundef | ...

data Block = Block [Stmt]

data Fundef = Fundef String [String] Block

data TopDef = TopFun Fundef

使用以下示例语法:

function long_function_name () = {
  let g() = {
    {
       h()
    };
    3
  } 
}

我正在尝试使用HughesPJ pretty库为该语言创建漂亮的打印机。到目前为止,我的尝试如下:

instance Pretty Stmt where
  pprint = \case
    SExpr e -> pprint e
    SBlock b -> pprint b
    SLet f -> text "let" <+> pprint f

instance Pretty Block where
  pprint (Block stmts) = lbrace $+$
    nest 2 (vcat (punctuate semi (map pprint stmts))) $+$ 
    rbrace

instance Pretty Fundef where
  pprint (Fundef name args body) = pprint name  <> parens (...) <+> text "=" <+> pprint body

instance Prettty TopDef where
  pprint (TopFun f) = text "function" <+> pprint f

问题是,我想在函数声明的同一行中包含{,但它总是使后面几行相对于括号列缩进,而不是绝对的。应该在上面的示例的漂亮字体中可见;

function long_function_name () = {
                                   let g() = {
                                               {
                                                 h()
                                               };
                                               3
                                             } 
}

为什么会发生这种情况,我该如何解决这个问题?我想尽可能避免重复代码

解决方法

您在正文之前写了<+>,因此$+$的垂直串联完全在function行的水平串联中,因此全部缩进了。我相信,pretty的用途是在块上进行显式匹配,因为它是垂直布局的一部分,即:

pPrint (Fundef name args (Block stmts)) = vcat
  [ pPrint name <> parens (...) <+> text "=" <+> lbrace,nest 2 (vcat (punctuate semi (map pPrint stmts))),rbrace
  ]

prettyprinter这样的更现代的漂亮打印库使此操作变得容易一些:nest(或indenthang)处理行缩进 跟随第一行以垂直布局排列,因此您可以将nest放在左括号和主体之间,并将右括号放在嵌套外部,如下所示:

"prefix" <+> vcat
  [ nest 4 $ vcat
    [ "{","body"
    ],"}"
  ]

prefix {
  body
}

(注意。您可以像这样使用OverloadedStrings而不是将文字包装在text中。)

但这不适用于prettyprettyprinter似乎是为了使一切杂乱无章。

我还建议您使用group的其他优点,例如,一个{{1}}函数可让您表达“如果合适,可将其放在一行上”,这对于使格式化稳固非常有用。并响应不同的渲染上下文。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。