如何将模式绑定到数据结构中的特定项?

Dav*_*vid 3 haskell

考虑下面的简单数据结构(我正在学习如何使用attoparsec).我没有自动导出节目,而是为它创建了一个实例.但是,如果DateDefinition中项目的顺序发生了变化,那么该实例将立即中断(返回错误答案)(例如,我将dayOfMonth放在monthOfYear之前).必须有一种方法可以将模式中的每个条目与数据结构中的每个条目相关联,这样它就不会受到项目顺序的变化的影响.但是怎么样?我尝试使用实际的名称,但不出所料,这不起作用,只是导致关于阴影现有绑定的警告.

data DateDefinition = DateDefinition
            {
                 monthOfYear :: Months,
                 dayOfMonth :: Int,
                 hourOfDay :: Int,
                 minuteOfHour :: Int,
                 secondOfMinute :: Int
            }

instance Show DateDefinition where
   show (DateDefinition m d _ _ _) = show m  ++  " " ++ show d
Run Code Online (Sandbox Code Playgroud)

bhe*_*ilr 5

您可以直接使用字段访问者; 这是最简单的方法:

instance Show DateDefinition where
    show dd = show (monthOfYear dd) ++ " " ++ show (dayOfMonth dd)
Run Code Online (Sandbox Code Playgroud)

或者,您可以使用RecordWildCards扩展名:

instance Show DateDefinition where
    show DateDefinition{..} = show monthOfYear ++ " " ++ show dayOfMonth
Run Code Online (Sandbox Code Playgroud)

如果你从来没有打算摆脱这些领域,这是很好的.如果你想改变内部结构而不破坏任何东西,那么第一个实现(如rampion所指出的)可能是最安全的.只要不导出构造函数,就可以随时将这些字段设置为普通函数而无需任何人知道.

  • @David如果你还没到那儿,那就别担心了.对于像这样简单的事情,你可能无论如何都不需要它们.只需坚持使用普通的旧字段访问器,编写单独的函数以根据需要设置不同的值,并且不要在构造函数上进行模式匹配.您最终可能不会编写最短的代码,但可以保证它比其他解决方案更具可读性和更具前瞻性. (2认同)