为什么在Haskell中'minimum(1,2)`返回2?
为什么最小值(1,2)在Haskell中是2 我在GHCi的测试结果为什么在Haskell中'minimum(1,2)`返回2?,haskell,Haskell,为什么最小值(1,2)在Haskell中是2 我在GHCi的测试结果 GHCi, version 8.2.1: http://www.haskell.org/ghc/ :? for help Prelude> minimum (1, 2) 2 它不应该返回1吗?当您查看时,您会发现最小值可以有各种输入(在参数类型的意义上) 在您的例子中,您希望对minimum函数应用列表,以获得最小元素,因此请尝试 minimum [1,2] 最小值的类型为 (Ord a, Foldable t)
GHCi, version 8.2.1: http://www.haskell.org/ghc/ :? for help
Prelude> minimum (1, 2)
2
它不应该返回1吗?当您查看时,您会发现最小值可以有各种输入(在参数类型的意义上)
在您的例子中,您希望对minimum函数应用列表
,以获得最小元素,因此请尝试
minimum [1,2]
最小值的类型为
(Ord a, Foldable t) => t a -> a
pairs的实例仅引用pair的第二个元素,您可以使用toList
:
toList (1,2)
> [2]
该集合中的最小元素为2
此行为的原因有两个:
- 由于,像
minimum
或length
这样的函数(即将容器结构简化为单个值的函数)不再只在列表上运行,而是在一般实例上运行。这非常有用,例如,您可以直接计算数组、map或trie的最小值,而无需首先将其转换为列表。(在FTP之前,表达式可能只是一个类型错误,因为参数不是列表,而是元组。)
- 元组是函子,特别是在第二个参数中,它们是函子。这允许你做一些事情,比如
Prelude> fmap (+1) <$> [("Bla",2), ("blub",3)]
[("Bla",3),("blub",4)]
Prelude>fmap(+1)[(“Bla”,2),(“blub”,3)]
[(“Bla”,3),(“blub”,4)]
这是第二个论点,因为(a,b)
实际上是(,)a)b
的语法糖,也就是说,我们在这里处理的是(,)a
函子。这是创建Haskell元组函子实例的唯一可能方法
IMHO,拥有这个实例并不是一个很好的特性,因为元组在这些元素之间应该是对称的。Haskell元组不是对称的,它们是“包含一个多态元素的容器”,即第二个
这本身并不太糟糕,但元组也有一个可折叠的实例:一旦确定元组是第二个元素的容器,自然也希望对其运行反变形。它们不是非常令人兴奋的反态射,只在一个元素上工作,特别是令人困惑的是,即使第一个元素具有相同的类型,反态射也会忽略它。但哦,好吧,我们到了
†编写上述内容的正确方法是IMOsecond(+1)[(“Bla”,2),(“blub”,3)]
,使用,这相当于元组上的fmap
,但避免了两个元素之间的混淆。(此外,它更通用,但不会对大多数应用程序产生影响:它可以与通用箭头一起使用,而不仅仅是与函数一起使用。)Minimum是一个在列表上工作的函数。您可能正在查找min
。也就是说,我不确定这里到底发生了什么有趣的事情,可能是元组作为列表之类的身份。我记得几天前的一个问题,我想是类似的。(FWIW,我认为是a。)注意最小值(True,3)
也会进行类型检查,并计算为3
。这是因为可折叠实例是可折叠的((,)a)
,所以只有第二个组件重要。事实上,我们不能在两种不同类型的组件之间取最小值。。。。而且它不能在列表中同时包含这两个组件,因为toList(“hello”,2)
也会进行类型检查,但是[“hello”,2]
不会。