为何启用DerivingStrategies后Cabal仍需GeneralizedNewtypeDeriving?
问题原因解析
核心差异来自Cabal与GHC默认使用的语言模式不一致:
- 直接用
ghc编译单个文件时,GHC默认采用基于Haskell98的宽松模式,附带启用了多个默认扩展。在这个模式下,启用DerivingStrategies后会自动支持deriving newtype语法,不需要额外启用GeneralizedNewtypeDeriving。 - 你的Cabal项目未指定
default-language字段,Cabal 3.8及以上版本会默认使用Haskell2010标准语言模式。在这个严格的标准模式下,GHC要求显式启用GeneralizedNewtypeDeriving,即使你已经开启了DerivingStrategies。
解决方法
你可以任选以下两种方式解决:
方式1:对齐GHC默认语言模式
在Cabal文件中添加default-language: GHC2021(或对应GHC版本支持的更高GHC语言标准),这样就和直接用ghc编译的行为一致,无需额外扩展:
cabal-version: 3.8 name: foo version: 1.0 executable foo main-is: main.hs build-depends: base default-language: GHC2021
方式2:显式启用所需扩展
保持Cabal默认的Haskell2010模式,在源文件中额外添加GeneralizedNewtypeDeriving扩展声明:
{-# LANGUAGE DerivingStrategies #-} {-# LANGUAGE GeneralizedNewtypeDeriving #-} newtype MyNum = MyNum Int deriving stock (Eq, Ord, Show, Read) deriving newtype (Num, Enum, Real, Integral) main :: IO () main = print $ MyNum 0
内容的提问来源于stack exchange,提问作者Enlico
相关产品推荐
相关产品推荐

