You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Haskell中使用$运算符出现类型错误的问题排查

Haskell $运算符相关类型错误解析

1. 初始类型歧义的原因

(2^) $ (*30) $ 2 + 2的类型冲突源于Haskell的类型推断规则:

  • (2^)的类型是Integral a => a -> a,要求参数是整数类型
  • (*30)的类型是Num b => b -> b,支持所有数值类型
  • 2+2是Num c => c,无具体类型约束

默认情况下GHCI的ExtendedDefaultRules扩展会帮我们把这类歧义类型默认解析为Integer,但偶尔会因为会话中之前的类型上下文干扰,导致扩展失效,出现"无法推导Num t10"的歧义错误。重启GHCI后,之前的上下文被清空,默认规则重新生效,表达式就能正常运行。

2. 重新定义$后的错误根源

标准库的$运算符有两个关键属性:

  • 最低优先级(优先级0)
  • 右结合性(声明为infixr 0 $)

你手动输入的f $ a = f a虽然逻辑上和标准$一致,但丢失了优先级和结合性声明,GHCI会用这个自定义版本覆盖默认的$。这直接改变了表达式的运算顺序:

  • 标准$下,表达式等价于(2^) ((*30) (2 + 2)),运算顺序符合预期
  • 自定义$后,表达式被解析为((2^) $ (*30)) + 2,也就是((2^) (*30)) + 2——此时(2^)需要接收一个整数,但(*30)是函数类型,完全不匹配,直接触发类型错误。

同时,自定义$也会干扰GHCI的类型推断逻辑,进一步加剧类型歧义问题。

内容的提问来源于stack exchange,提问作者Jon

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.07 15:47:36