在编写重载字符串时如何删除样板?

时间:2013-06-15 17:21:28

标签: haskell template-haskell

给出以下代码:

{-# LANGUAGE OverloadedStrings #-}

newtype Firstname = Firstname String deriving (Eq, Show)
instance IsString Firstname where fromString = Firstname

newtype Lastname = Lastname String deriving (Eq, Show)
instance IsString Lastname where fromString = Lastname

data Person = Person { firstname :: Firstname, lastname :: Lastname, age :: Int } deriving Show

我想删除围绕创建强类型字符串的样板。有可能使用Template Haskell(或其他一些方法)来实现这个目标吗?

例如:

{-# LANGUAGE OverloadedStrings, TemplateHaskell #-}

$(strongString ''Firstname)
$(strongString ''Lastname)

data Person = Person { firstname :: Firstname, lastname :: Lastname, age :: Int } deriving Show

1 个答案:

答案 0 :(得分:15)

使用GeneralizedNewtypeDeriving并为IsStringFirstname派生Lastname个实例。您的示例的示例代码如下:

{-# LANGUAGE OverloadedStrings, GeneralizedNewtypeDeriving #-}
import Data.String

newtype Firstname = Firstname String deriving (Eq, Show, IsString)

newtype Lastname = Lastname String deriving (Eq, Show, IsString)

data Person = Person { firstname :: Firstname
                     , lastname :: Lastname
                     , age :: Int
                     }

foo = Person "hello" "world" 10

您可以使用TH编写您想要的类似功能,但将这些功能保存在单独的模块中然后在此处导入它们是不值得的。