Haskell - 多种数据类型的 Show 实例

3

我目前正在为学校任务制作一个国际象棋游戏,我的棋子已经定义好了。

    data Piece = Piece { piecetype :: PieceType, color :: PieceColor }
    data PieceType = Pawn | Knight | Bishop | Rook | Queen | King
    data PieceColor = Black | White deriving Eq

现在我需要将棋子打印成单个字符(国王= k,皇后= q,骑士= n等)。对于黑色棋子,其值为相应白色棋子的大写字母(国王= K,皇后= Q,骑士= N等)。

因此,我创建了三个show的实例。

    instance Show PieceColor where
        show Black = "B"
        show White = "W"

    instance Show PieceType where
        show Pawn = "P"
        show Knight = "N"
        show Bishop = "B"
        show Rook = "R"
        show Queen = "Q"
        show King = "K"

第三个问题是什么?
    instance Show Piece where
        show (piecetype, color) = show piecetype 
                                  if show color == "W"
                                  then show piecetype
                                  else toUpper (show piecetype)

我收到了以下错误信息(我尝试了很多,但根据这个链接,看起来我已经非常接近 类似的东西).
Couldn't match expected type `Piece' with actual type `(t0, t1)'

我感激任何帮助。 顺祝商祺,Me


应该是 show (Piece piecetype color) 而不是 show (piecetype,color) - Satvik
我的一些错误已经修复了,现在它像魔法一样运行了,谢谢 Satvik。 - M4st3rM1nd
1个回答

8

直接回答:

instance Show Piece where
    show (Piece piecetype Black) = map toLower $ show piecetype
    show (Piece piecetype White) = show piecetype

解释:

  • Piece是一个带有构造函数Piece的数据类型(类型名和构造函数在您的情况下都相同),而不是元组。因此,您应该对构造函数进行模式匹配,而不是对元组进行匹配。

  • toUppertoLower存在于Data.Char中,并且作用于Char,而像"B"这样的东西是StringString[Char]的类型别名)。因此,要将String大写,可以使用map toUpper

  • 比较字符串如show color == "B"并不是很有效,相反您可以对构造函数名称进行模式匹配。


3
我建议直接对颜色进行模式匹配,而不是像这样写 if show color == "B" ... - hammar

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接