一些库使用 unsafeCoerce
暂时满足约束:
class Given a where given :: a
newtype Gift a r = Gift (Given a => r)
give :: forall a r. a -> (Given a => r) -> r
give a k = unsafeCoerce (Gift k :: Gift a r) a
(此示例来自反射软件包。Singletons软件包还使用了此技巧。)
为什么此unsafeCoerce
安全?是否有任何官方文件保证Given a => r
和a -> r
在GHC中具有相同的运行时表示?
没有官方文件保证。埃德·克梅特(Ed Kmett)依靠他对GHC内部运作的了解。他知道的:
- 在GHC Core,
->
和=>
实际上是同一件事。 - 单人类类实例的字典像newtypes— the dictionary is 是方法。
我实际上写了一份提议来合法地进行此操作,但是正确容纳所有用例很棘手。