一个Haskell函数,它接收不同类型的列表并只返回整数列表

一个Haskell函数,它接收不同类型的列表并只返回整数列表,haskell,types,Haskell,Types,我有这样一个函数: [(String, [Int], Int)] function :: [(String, [Int], Int)] function = [("R1",[6,10,14],6),("R2",[8,10,14],8),("R3",[11,15,24],11)] 我需要一个只返回[Int]列表的函数 输入示例: [("R1",[6,10,14],6),("R2",[8,10,14],8),("R3",[11,15,24],11)] 输出示例(我希望输出的行为): 我一直在考

我有这样一个函数:

[(String, [Int], Int)]
function :: [(String, [Int], Int)]
function = [("R1",[6,10,14],6),("R2",[8,10,14],8),("R3",[11,15,24],11)]
我需要一个只返回[Int]列表的函数

输入示例:

[("R1",[6,10,14],6),("R2",[8,10,14],8),("R3",[11,15,24],11)]
输出示例(我希望输出的行为):

我一直在考虑创建一个输入函数,如下所示:

[(String, [Int], Int)]
function :: [(String, [Int], Int)]
function = [("R1",[6,10,14],6),("R2",[8,10,14],8),("R3",[11,15,24],11)]
还有一个是我想要的,像这样:

convert :: [(String, [Int], Int)] -> [Int]
convert [] = []
...

如何开发转换函数?

我想做的第一件事是列出我认为需要的所有类型签名:

-- Something to use with fmap to get rid of the Strings
f :: (String, [Int], Int) -> ([Int], Int)

-- Something to cons the list with the Int
g :: ([Int], Int) -> [Int]

-- Our final goal:
convert :: [(String, [Int], Int)] -> [Int]
现在,我想思考如何将这些组合在一起,以获得最终结果:

fmap g . fmap f :: [(String, [Int], Int)] -> [[Int]]
多亏了这一点,您可以将其改写为:

fmap (g . f) :: [(String, [Int], Int)] -> [[Int]]
这很接近,但我们有两个嵌套列表,而不是一个。幸运的是列表是一个,这意味着我们可以使用
mconcat::[a]->a
来折叠它。这有点让人困惑,因为
mconcat
操作的是一个单像
a
值列表。在我们的例子中,
mconcat
更具体的签名是:

mconcat :: [[Int]] -> [Int]
其中,
monoid
我们是
mapping
是内部列表

不管怎样,我们可以这样做:

mconcat . fmap (g . f) :: [(String, [Int], Int)] -> [Int]
这正是我们试图实现的功能:

convert :: [(String, [Int], Int)] -> [Int]
convert = mconcat . fmap g . fmap f
    where f = undefined
          g = undefined
现在我们只需要实现
f
g

f :: (String, [Int], Int) -> ([Int], Int)
f (_, xs, x) = (xs, x)

g :: ([Int], Int) -> [Int] 
g (xs, x) = x:xs

g' :: ([Int], Int) -> [Int] 
g' (xs, x) = xs ++ [x]
根据您希望
x
进入的位置,您可以使用
g
g'

然后您的最终实现将是类似的(添加到组合中以匹配示例结果):

回顾你的问题,看起来三元组的第三个元素总是第二个元素的成员?如果是这种情况,此函数将变得更简单:

convert :: [(String, [Int], Int)] -> [Int]
convert = sort . mconcat . fmap f
    where f (_, xs, ) = xs

如果由于最后的排序步骤而担心性能,可以使用
foldr
to而不是
mconcat
将其与级联结合起来,并在
a->b->b
中进行排序

提示:使用
map
ping。首先编写一对类型为
[(String,[Int],Int)]->([[Int]],[Int])
([[Int]],[Int])->[Int])
的助手函数。(第一个可能会从另一个类型为
(String,[Int],Int)->([Int],Int)
)的助手那里受益。不要害怕定义大量的小函数。)“我有一个这样的函数:
”[(String,[Int],Int)]”
”是什么意思?你调用的
函数不是函数;这只是一个元组列表。