Haskell 在'中键入声明;其中';——什么';发生什么事了?
在阅读时,我遇到了以下示例:Haskell 在'中键入声明;其中';——什么';发生什么事了?,haskell,types,where-clause,Haskell,Types,Where Clause,在阅读时,我遇到了以下示例: prop_RevRev xs = reverse (reverse xs) == xs where types = xs::[Int] 手册接着说: 属性必须具有单态类型`多态性属性(如上面的属性)必须限制为用于测试的特定类型。这样做很方便,可以在 其中类型=(x1::t1,x2::t2,…) 条款。请注意,类型不是一个关键字;这只是一个本地声明,它提供了一个方便的地方来限制x1、x2等的类型 我以前在哈斯克尔从没见过这样的把戏。以下是我真正遇到的问题: 为什
prop_RevRev xs = reverse (reverse xs) == xs
where types = xs::[Int]
手册接着说:
属性必须具有单态类型`多态性属性(如上面的属性)必须限制为用于测试的特定类型。这样做很方便,可以在
其中类型=(x1::t1,x2::t2,…)
条款。请注意,类型不是一个关键字;这只是一个本地声明,它提供了一个方便的地方来限制x1、x2等的类型
我以前在哈斯克尔从没见过这样的把戏。以下是我真正遇到的问题:
prop_RevRev :: [Int] -> Bool
prop_RevRev xs = reverse (reverse xs) == xs
的这种用法是否构成了类型声明的“特殊”语法?或者它是一致的和合乎逻辑的(如果是,如何?)
其中
不是类型声明的特殊语法。例如,这项工作:
prop_RevRev :: [Int] -> Bool
prop_RevRev xs = ys == xs
where ys = reverse (reverse xs)
这也是:
prop_RevRev xs = ys == xs
where ys = reverse (reverse xs)
ys :: [Int]
where type=(xs::[Int])
优于prop\u revrevrev::[Int]->Bool
的优点是,在后一种情况下,您必须指定返回类型,而在前一种情况下,编译器可以为您推断返回类型。如果您有一个非Boolean属性,这将很重要,例如:
prop_positiveSum xs = 0 < length xs && all (0 <) xs ==> 0 < sum xs
where types = (xs :: [Int])
read "Just True" :: (Maybe Bool)
prop_positiveSum xs=0
它没有特殊语法,有时您只需要它,如以下情况:
foo :: String -> String
foo s = show (read s)
目前,无法键入该类型,因为无法识别值read s
的类型。已知的是,它必须是Show和read的实例。但该类型根本不会出现在类型签名中,因此也不可能保留该类型并推断出受约束的类型。(只是没有可以约束的类型变量。)
值得注意的是,reads
的功能完全取决于给reads
的类型签名,例如:
prop_positiveSum xs = 0 < length xs && all (0 <) xs ==> 0 < sum xs
where types = (xs :: [Int])
read "Just True" :: (Maybe Bool)
将成功,而
read "Just True" :: (Maybe Int)
不会。我也一直在想这个问题。谢谢。@MattFenwick:您可以在任何级别向任何子表达式添加类型批注,因此,当您只想填写编译器无法推断的细节,而不必指定完整的类型签名时,此技巧非常有用。但是,它们仍然必须保持一致例如,
(x::Float)+(x::Int)
将导致类型错误。因此基本上,类型
或类型
是一个虚拟变量,不使用;只是为了方便另一个类型的保护expression@newacct:是,但不能使用类型
,因为这是保留关键字:)