繁体   English   中英

如何在Haskell中实现数据类型的自定义排序?

[英]How to implement custom ordering for data types in Haskell?

假设我有一个数据类型,表示像这样的一副扑克牌

data Suit = Clubs | Spades | Hearts | Diamonds deriving (Eq)

instance Show Suit where
    show Diamonds = "♦"
    show Hearts = "♥"
    show Spades = "♠"
    show Clubs = "♣"

data Value = Two | Three | Four | Five | Six | Seven | Eight | Nine | Ten | Jack | Queen | King | Ace deriving (Eq, Ord)

data Card = Card {
      value :: Value
    , suit :: Suit
    } deriving (Eq, Ord)

实例Show Card,其中show(Card vs)= show s ++ show v

Haskell通过允许我导出EqOrd而无需明确指定这些关系,已经对我有很大帮助。 这特别有用,因为我想使用Ord根据扑克规则最终比较两只手的价值。

现在在扑克中,西装的顺序实际上并不重要。 因此我尝试了

instance Ord Suit where
    compare Clubs Spades = EQ
    compare Clubs Hearts = EQ
    compare Clubs Diamonds = EQ
    compare Spades Hearts = EQ
    compare Spades Diamonds = EQ
    compare Hearts Diamonds = EQ

这已经有点冗长了……甚至不起作用:

*P054> a
♠A
*P054> b
♣A
*P054> a < b
*** Exception: P054.hs:(12,9)-(17,36): Non-exhaustive patterns in function compare

那么,如何在Suit上正确定义一个顺序,以表达所有西服都相等的事实呢?

你缺少几个组合,比如所有Clubs在右手边。 如果所有条件相等,那么不管输入什么, compare的可能结果是什么? 只有一个: EQ 因此,我们甚至不需要查看ab

instance Ord Suit where
    compare _ _ = EQ

但是,该Ord实例却毫无用处。 或者,您可以为Card创建自定义实例,

instance Ord Card where
    compare a b = compare (value a) (value b)
    -- compare = compare `on` value -- using `on` from Data.Function
    -- compare = comparing value    -- using `comparing` from Data.Ord

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM