为什么给列表整数逐个加值的SML函数会报类型不匹配错误?
问题核心原因
你定义的inclist函数的两个匹配分支混用了Standard ML中两种完全不同的参数传递形式,导致函数推导类型和你预期的调用方式不匹配:
- 第一个分支
fun inclist [] 0 = []是柯里化多参数写法,参数之间用空格分隔,等价于函数接收两个独立的参数,第一个是整数列表,第二个是增量值 - 第二个分支
inclist (l, inc) = ...是元组单参数写法,把两个参数打包成一个int list * int类型的元组作为唯一入参
Standard ML编译器会以你第二个分支的参数形式为准,推导出inclist的类型是int list * int -> int list,也就是该函数只能接收一个包含列表和增量的元组作为入参。你调用时应该是用了柯里化的写法inclist [1,2,3,4,5] 1,就会触发两类报错:
- 第一个入参
[1,2,3,4,5]是int list类型,和函数要求的int list * int元组类型不匹配 - 传完第一个入参后
inclist [1,2,3,4,5]返回的是int list类型,本身不是函数,无法再接收第二个增量参数1
修复方案
有两种统一参数形式的修复方法,任选其一即可:
方案1:统一使用元组参数形式
把第一个分支也修改为元组匹配模式:
fun inclist ([], 0) = [] | inclist (l, inc) = map (fn x => x + inc) l;
调用时传入元组即可:inclist ([1, 2, 3, 4, 5], 1)
方案2:统一使用柯里化参数形式
把第二个分支修改为柯里化的参数形式:
fun inclist [] 0 = [] | inclist l inc = map (fn x => x + inc) l;
调用时直接传两个独立参数即可:inclist [1, 2, 3, 4, 5] 1
你之前编写的乘法函数可以正常运行,大概率是因为定义时两个分支的参数形式保持了统一,没有出现柯里化和元组参数混写的问题。
内容的提问来源于stack exchange,提问作者Grav
相关产品推荐
相关产品推荐

