Loading [MathJax]/jax/output/CommonHTML/config.js
首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
社区首页 >问答首页 >为什么这两个函数有不同的类型?

为什么这两个函数有不同的类型?
EN

Stack Overflow用户
提问于 2018-07-29 03:57:41
回答 1查看 68关注 0票数 1

我有两个功能

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> a) f b b)

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> 0) f b b)

我试着用手找出这些函数的类型

代码语言:javascript
运行
AI代码解释
复制
(t1 -> t1 -> t2) -> t1 -> t2

代码语言:javascript
运行
AI代码解释
复制
Num t3 => (t1 -> t1 -> t2) -> t1 -> t3

但是,当我使用GHCI使用:t获取类型时,我得到以下信息

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> a) f b b) :: (t1 -> t1 -> t2) -> t1 -> t2
(\f b -> (\a -> 0) f b b) :: Num (t1 -> t1 -> t2) => p -> t1 -> t2

我不明白如何将\a -> a更改为\a -> 0将第一个参数从(t1 -> t1 -> t2)更改为p

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2018-07-29 04:19:47

导出(\f b -> (\a -> a) f b b)的类型

那么,让我们尝试导出表达式的类型:

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> a) f b b)

或者更详细:

代码语言:javascript
运行
AI代码解释
复制
(\f -> (\b -> (((\a -> a) f) b) b))

我们在这里看到,这是一个接受两个参数的函数(从技术上讲,函数总是有一个参数,这个函数的结果可以是另一个参数,但是假设如果我们讨论“两个参数”,我们指的是这样的结构)。

因此,参数是fb,最初我们对这些参数不太了解,因此我们为它们分配了一个类型,表达式如下:

代码语言:javascript
运行
AI代码解释
复制
f :: g
b :: h
(\f b -> (\a -> a) f b b) :: g -> (h -> i)

因此,我们创建了三种类型的ghi (这里我使用了abc以外的其他标识符,因为这可能导致与变量混淆)。

但是我们还没有完成,因为表达式本身可以对类型的行为带来更多的限制。例如,我们看到一个lambda表达式:\a -> a,它显然具有类型:

代码语言:javascript
运行
AI代码解释
复制
\a -> a :: j -> j

接下来,我们看到一个函数应用程序,函数是\a -> a,参数是f,这意味着g ~ j (gj是相同的类型),(\a -> a) f的类型是(\a -> a) f :: g

但是我们还没有完成,因为(\a -> a) f的结果现在在b的函数应用程序中充当一个函数,因此这意味着g实际上是一个函数,具有输入类型h和一些(当前未知的输出类型),因此:

代码语言:javascript
运行
AI代码解释
复制
g ~ (h -> k)

所以(\a -> a) f b的类型是k,但是我们还没有完成,因为我们执行另一个函数应用程序,(\a -> a) f b作为函数(类型k),b作为参数,这意味着k实际上是一个函数,h是参数类型,结果是表达式的类型,所以i。这意味着我们有:

代码语言:javascript
运行
AI代码解释
复制
g ~ j
g ~ (h -> k)
k ~ (h -> i)

换句话说,表达式的类型是:

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> a) f b b) :: (h -> (h -> i)) -> (h -> i)

或者不那么冗长:

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> a) f b b) :: (h -> h -> i) -> h -> i

导出(\f b -> (\a -> 0) f b b)的类型

派生的第一步大致相同,我们首先引入一些类型变量:

代码语言:javascript
运行
AI代码解释
复制
f :: g
b :: h
(\f b -> (\a -> 0) f b b) :: g -> (h -> i)

现在我们开始做推论。我们首先推断出(\a -> 0)的类型。这是一个函数,类型为Num l => j -> l,因为0Number,但它可以是任何Num类型,并且与参数a的类型无关。

接下来,我们看到有一个函数调用,函数以(\a -> 0)为函数,f为参数,因此我们得出了g ~ j的结论。此函数调用的结果类型为(\a -> 0) f :: Num l => l

现在我们看到了另一个函数调用,函数是(\a -> 0) f,参数是b。因此,我们得出结论,l是一个函数(所以是l ~ (h -> k))。

最后一个函数调用是以(\a -> 0) f b :: k作为函数,b再次作为参数。这意味着k是一个函数k ~ h -> i。因此,我们得到了以下类型和等式:

代码语言:javascript
运行
AI代码解释
复制
f :: g
b :: h
(\a -> 0) :: Num l => j -> l
(\f b -> (\a -> 0) f b b) :: g -> (h -> i)
g ~ j
l ~ (h -> k)
k ~ (h -> i)

因此,表达式的类型如下:

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> 0) f b b) :: g -> (h -> i)

或者更具体地说:

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> 0) f b b) :: Num (h -> (h -> i)) => g -> (h -> i)

或者不那么冗长:

代码语言:javascript
运行
AI代码解释
复制
(\f b -> (\a -> 0) f b b) :: Num (h -> h -> i) => g -> h -> i

因此,既然我们使用(\a -> 0)作为内部lambda表达式,那么f的类型和值就不再相关了。(\a -> 0) f将始终返回0,这应该是一个可以考虑b的函数。

至少从理论上看,作为Num的函数没有什么“奇怪”(只要它支持应该由Num类型实现的函数)。例如,我们可以实现一个函数instance Num (a -> b -> Int),从而将0看作总是映射到0的常量函数,而(+)则是构造将这两个函数相加在一起的新函数的一种方法。

票数 3
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/51580107

复制
相关文章
【Python】列表 List ⑦ ( 列表遍历 | 使用 while 循环遍历列表 | 使用 for 循环遍历列表 | while 循环 与 for 循环对比 )
将 列表 容器 中的数据元素 , 依次逐个取出进行处理的操作 , 称为 列表的遍历 ;
韩曙亮
2023/10/11
9810
Java之while循环基本使用
while 循环控制 1. 基本语法 2. while 循环执行流程分析 While01.java 画出流程图 使用 while 循环完成前面的题 //输出10句 你好,兮动人 int i = 1; //循环变量初始化 while( i <= 10 ) {//循环条件 System.out.println("你好,兮动人" + i);//执行语句 i++;//循环变量迭代 } System.out.println("退出while ,继续.." + i); // 11
玖柒的小窝
2021/09/17
7180
Java之while循环基本使用
Java之while循环基本使用
文章目录 while 循环控制 1. 基本语法 2. while 循环执行流程分析 3. 注意事项和细节说明 4. 课堂练习题 while 循环控制 1. 基本语法 2. while 循环执行流程分析
兮动人
2021/06/11
6330
Java之while循环基本使用
基础知识:if条件、while循环、fo
1、实现用户输入用户名和密码,当用户名为 seven 且 密码为 123 时,显示登陆成功,否则登陆失败!
py3study
2020/01/17
5790
while循环嵌套while循环
《代码大全》推荐先用伪代码来写框架,从最上层思考可以将抽象能力最大化,不会先陷入任何编程语言的实现细节中,通俗地说就是在蓝图层面解决问题。
不会飞的小鸟
2021/07/30
3.6K0
使用while循环打印颜色相隔表格
<?php //手动画表格相当于画二维数组 header("Content-Type:text/html; charset=utf8"); echo "<table bord
闵开慧
2018/03/30
1.2K0
软件测试|最全的Python for循环和while循环使用介绍
循环简单来说就是让一段代码按你想要的方式多次运行。软件拥有强大的运算能力,就是由循环提供的。
霍格沃兹测试开发Muller老师
2023/02/07
1.4K0
Js基础教程之while条件循环语句
JavaScript基础教程之while 一、while while (条件) { 要执行的代码块 } continue 不执行while后面语句,重新循环 break 跳出while语句 while (i < 10) { if(i==8) { i++; continue; } text += "数字是 " + i; if(i==9) break; i++; } console.log(text); 二、do while 至少执行一次 do { 要
老雷PHP全栈开发
2020/07/02
2.4K0
请停止在 React 中使用“&&”进行条件渲染
英文 | https://javascript.plainenglish.io/its-2023-please-stop-using-for-conditional-rendering-in-react-b588a09ebb17
winty
2023/08/23
2660
请停止在 React 中使用“&&”进行条件渲染
Java之do while循环控制语句基本使用
文章目录 do..while 循环控制 1. 基本语法 2. 说明: 3. do...while 循环执行流程分析 4. 注意事项和细节说明 5. 课堂练习题 do…while 循环控制 1. 基本语法 循环变量初始化; do{ 循环体(语句); 循环变量迭代; }while(循环条件); 2. 说明: do while 是关键字 也有循环四要素, 只是位置不一样 先执行,再判断,也就是说,一定会至少执行一次 最后 有一个 分号 ; while 和 do…while 3. do…while 循环执行流程分
兮动人
2021/06/11
8790
Java之do while循环控制语句基本使用
python流程控制之while循环的使用
while 条件:  执行代码 当条件条件成立,代码就会执行; count = 0  while count <= 100 : #只要count<=100就不断执行下面的代码    print("loop ", count )    count +=1    死循环: 有一种循环叫死循环,一经触发,就会一直运行。 while 是只要后边条件成立(也就是条件结果为真)就一直执行 count = 0 while True:     print("你是风儿我是沙,缠缠绵绵到天涯...",count)     
py3study
2020/01/14
1.1K0
python学习笔记(5)循环语句while,for的使用
python编程中的While语句用于循环执行程序,即在某条件下,执行某段程序,常常与if…else,for语句一起连用,下面是Whlie循环的基本形式:
大数据小禅
2021/08/16
1.5K0
python学习笔记(5)循环语句while,for的使用
While循环
While(条件)//如果条件为真则一直执行循环体中的内容 { 循环体 } 示例1 提示用户输入密码 888正确 若不正确继续输入 且只有三次重新输入的机会
用户7272142
2023/10/11
1630
while()循环
回顾一下java基础的while(true)循环,有时候实际项目中也会看到在用。本小节来梳理一下
在水一方
2022/06/14
1.5K0
while()循环
Java基础知识-循环语句的使用介绍(for、while、do-while)
本文介绍了循环语句在Java中的三种实现方式,分别是for循环、while循环和do-while循环。每种循环都有其适用的场景和用法,需要根据具体情况进行选择。同时,还给出了每种循环的代码示例和用法建议。
林老师带你学编程
2018/01/04
3.3K0
while循环与do…while循环的区别
while 先判断再执行 不满足循环条件时 一次都不会执行 do…while 先执行再判断 不管任何情况都至少执行一次
是阿超
2021/10/15
2.8K0
# C#学习 -循环结构-while循环-do ...while 循环-for循环
C#程序的三大结构 顺序结构:程序的入口都是Main函数,代码从上往下,从左往右,依次执行; 分支结构:当我们的程序执行到某个位置的时候,进行条件判断,根据判断的结果来执行不同的操作; 循环结构:在满足某个条件的时候反复执行一个语句序列(循环)。
呆呆敲代码的小Y
2021/08/12
3.2K0
进阶分支语句和使用while循环及break语句
了解和使用分支语句和while循环及break语句,加入数学运算并配合for循环,使用计算变量进行累加或累减操作。
楚客追梦
2022/11/11
1K0
进阶分支语句和使用while循环及break语句
【Python】循环语句 ② ( while 嵌套循环 | 代码示例 - while 嵌套循环 )
while 嵌套循环 也是基于 空格缩进 , Python 中基于 空格缩进 判定代码逻辑的层次关系 ;
韩曙亮
2023/10/11
4790
【Python】循环语句 ② ( while 嵌套循环 | 代码示例 - while 嵌套循环 )
点击加载更多

相似问题

NGINX不是从本地主机服务,而是从127.0.0.1提供服务。

13

从Keystore获取privatekey

10

本地主机上的专用pypi服务器

11

使用javascript从本地主机服务获取数据

12

如何通过提供PrivateKey来获取RSA PublicKey?

50
添加站长 进交流群

领取专属 10元无门槛券

AI混元助手 在线答疑

扫码加入开发者社群
关注 腾讯云开发者公众号

洞察 腾讯核心技术

剖析业界实践案例

扫码关注腾讯云开发者公众号
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档
查看详情【社区公告】 技术创作特训营有奖征文