首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >组合模式

组合模式
EN

Stack Overflow用户
提问于 2015-08-10 01:38:31
回答 1查看 237关注 0票数 10

考虑以下数据类型和模式同义词:

代码语言:javascript
运行
复制
{-# LANGUAGE PatternSynonyms, NamedFieldPuns #-}

data Foo = Foo {
      a :: Int
    , b :: String
    , c :: Maybe Bool
}

pattern Bar a b <- Foo { a, b }
pattern Baz c <- Foo { c }

我想匹配一个Foo,但是abc都有。类似的东西(无效的Haskell):

代码语言:javascript
运行
复制
showit :: Foo -> String
showit (Bar a b & Baz c) = show a ++ b ++ show c

一种选择是使用ViewPattern

代码语言:javascript
运行
复制
dup :: a -> (a, a)
dup a = (a, a)

showall' :: Foo -> String
showall' (dup -> (Bar a b, Baz c)) = show a ++ b ++ show c

但这会导致一个非详尽的匹配警告。但是我们知道BarBaz是无可辩驳的,因此匹配它们也是无可辩驳的。

如何在没有编译器警告的情况下表达这一点?

这样做的动机是对大型数据类型的字段具有细粒度的模式同义词,并允许调用方提取与NamedFieldPuns记录类似的所需字段。模式同义词还不支持记录语法,但它正在开发中:https://ghc.haskell.org/trac/ghc/ticket/8582

在我的例子中,我不能公开模块中的构造函数,因为我使用的是“智能构造函数”模式,因此不能给调用者提供与NamedFieldPuns匹配记录模式的好处。

https://stackoverflow.com/a/25161749/3198498为灵感。我试图在这个答案中扩展这个想法,允许调用者任意提取n个m字段,以获得更大的值。

编辑:结果发现,PatternSynonyms和耗尽性检查存在一个相当大的问题:https://ghc.haskell.org/trac/ghc/ticket/10339,这似乎会使模式同义词在启用警告的情况下编译时非常不愉快。

EN

回答 1

Stack Overflow用户

发布于 2016-08-12 03:25:24

不确定这是否有帮助,但我会试试看。这些解决方案中的任何一个都是可以接受的吗?

代码语言:javascript
运行
复制
showit :: Foo -> String
showit x@(Bar a b) = show a ++ b ++ show (c x)

showit' :: Foo -> String
showit' x@(Bar a b) = show a ++ b ++ showthat x
  where
    showthat (Baz c) = show c
票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/31910536

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档