[英]Haskell: Find the minimum in custom data type
因此,我有一個自定義數據類型,我們將其稱為Struct
,定義如下:
data Struct = Struct [SubStruct] deriving (Read, Show)
data SubStruct = SubStruct (Int, Int) deriving (Read, Show)
我需要做的是遍歷Struct
所有元素,然后根據fst
然后根據snd
找到最小值。 我怎么做? 更具體地說,我想獲得另一個SubStruct
例如:
SubStruct (-2,-5)
,基於代碼中的示例。
目前,我首先這樣做:
import Data.List
import Data.Function (on)
import Data.List (sortBy)
data Struct = Struct [SubStruct] deriving (Read, Show)
data SubStruct = SubStruct (Int, Int) deriving (Read, Show )
struct s sx = Struct(s:sx)
subStruct :: (Int, Int) -> SubStruct
subStruct (x, y) = SubStruct (x, y)
substructs = Struct $ [subStruct (0,1), subStruct (-2, 3), subStruct (4,-5)]
results xs = sortBy (compare `on` fst) (substructs xs)
但是我得到這個錯誤:
Couldn't match expected type `t -> [(a, b)]'
with actual type `Struct'
Relevant bindings include
xs :: t (bound at bbox.hs:15:9)
results :: t -> [(a, b)] (bound at file.hs:15:1)
The function `substructs' is applied to one argument,
but its type `Struct' has none
In the second argument of `sortBy', namely `(substructs xs)'
In the expression: sortBy (compare `on` fst) (substructs xs)
為什么不使用unzip
功能。 如果我們定義一個輔助功能:
unSubStruct :: SubStruct -> (Int, Int)
unSubStruct (SubStruct p) = p
然后,可以將返回所需元素的函數編寫為:
getMin :: Struct -> SubStruct
getMin (Struct l) = SubStruct (minimum xs, minimum ys)
where
(xs, ys) = unzip $ map unSubStruct l
請注意,這將遍歷列表兩次。 如果您定義自己的minimum
版本對可以工作,則可以避免這種情況:
getMin :: Struct -> SubStruct
getMin (Struct l) =
SubStruct $ foldr1 minPair $ map unSubStruct l
where
minPair (x0, y0) (x, y) = (min x0 x, min y0 y)
您有一個SubStruct
列表,該列表與元組列表基本相同。
因此,僅使用通用功能的一種解決方案是:
result = SubStruct (min1, min2) where
min1 = minimum (map fst . list)
min2 = minimum (map snd . list)
list = case substructs of
Struct this -> map (\(SubStruct t) -> t) this
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.