TypeScript 中对【函数类型】的约束使用解读

news2024/9/30 17:29:18

概述

函数是JavaScript 中的 一等公民
概念:函数类型的概念是指给函数添加类型注解,本质上就是给函数的参数和返回值添加类型约束

在这里插入图片描述

声明式函数:

在 TypeScript 中,一个函数有输入和输出,需要对其进行约束,需要把输入和输出都考虑到。

其中函数声明式的类型定义较简单:

可以给要接收的参数指定类型,也可以给函数的返回值约束类型。

//函数表达式,命名函数
function add(a: number, b: number): number {
    return a + b
}

上述案例说明:

  • 当函数参数被注解类型之后,不但约束了传递参数的类型,还限制了参数为必填
  • 函数返回值被类型注解后,也限制了函数体内部 return 出去的值,必须要满足类型要求

函数添加类型注释的好处是:

  • 避免以为参数不对,导致的函数内部逻辑错误
  • 对函数起到说明作用

注意:
输入多余的(或者少于要求的)参数,是不被允许的

//函数表达式,命名函数
function add(a: number, b: number): number {
    return a + b
}
console.log(add(5, 2 , 1));

在这里插入图片描述

表达式函数

如果要我们现在写一个对函数表达式的定义,可能会写成这样:

//函数表达式,匿名函数
let sum = function (a: number, b: number): number {
    return a + b
}

还可以写成箭头函数

//函数表达式,回调箭头函数
let callback = (a: number, b: number): number => {
    return a + b
}

箭头函数 表达式 还可以使用 【类型别名】 来进一步简化函数类型注解

注意:类型别名 抽离类型的方式,只能运用在 箭头函数表达式中

type ADD = (a: number, b: number) => number //通过类型别名,对类型进行抽离,还可达到复用的效果。

let callback: ADD = (a, b) => {
    return a + b
}

let n = callback(12, 96)
console.log(n);  //108

这样也是可以通过编译的,不过事实上,上面的代码只对等号右侧的匿名函数进行了类型定义,而等号左边的 callback 和 sum,是通过赋值操作进行类型推论而推断出来的,严格意义上来说,在TS中,这并不是最完整的写法。所以完整的写法需要我们手动给 函数 添加类型,则应该是这样:

匿名函数完整版写法:

//函数表达式,命名函数
let sum: (a: number, b: number) => number = function (a: number, b: number): number {
    return a + b
}

箭头函数表达式完整版写法:

//函数表达式,回调箭头函数
let callback: (a: number, b: number) => number = (a: number, b: number): number => {
    return a + b
}

注意
千万不要混淆了 TypeScript 中的=>和 ES6 中的 =>在 TypeScript 的类型定义中,=>用来表示函数的定义,左边是输入类型,需要用括号括起来,右边是输出类型


可选参数和默认参数

可选参数:

前面提到的方式,如果输入多余的(或者少于要求的)参数,是不被允许的。但有时候,传递的参数是处于未知的,这时候就需要配置 可选参数了

Infinity 接口定义类型中的可选属性类似,我们用 ? 表示可选的参数

//声明式函数
function add(a: number, b?: number): number {
    return a + b
}
//函数表达式,命名函数
let sum: (a: number, b?: number) => number = function (a: number, b: number): number {
    return a + b
}
//函数表达式,回调箭头函数
let callback: (a: number, b?: number) => number = (a: number, b: number): number => {
    return a + b
}

// 这时候当我们只一个参数值的时候,也不会报错!!!
console.log(add(5));
console.log(sum(3));
console.log(callback(9));

注意:

定义可选参数后,可选参数必须接在必需参数后面。换句话说,可选参数后面不允许再出现必需参数了,可选参数可以不传,但是一但传了,也依然需要约束其类型。

在这里插入图片描述

参数默认值

在 ES6 中,我们允许给函数的参数添加默认值,TypeScript 中会将添加了默认值的参数自动识别为可选参数

值得注意: 除声明式函数可以直接赋值默认值外,函数表达式,以及回调函数表达式,定义默认值,必须要搭配 ?可选属性。

//函数声明 ,命名函数
function add(a: number, b: number = 123): number {
    return a + b
}
//函数表达式,命名函数
let sum: (a: number, b?: number) => number = function (a: number, b: number = 798): number {
    return a + b
}
//函数表达式,回调箭头函数
let callback: (a: number, b?: number) => number = (a: number, b: number = 456): number => {
    return a + b
}

console.log(add(5));
console.log(sum(3));
console.log(callback(9));

此时就不受「可选参数必须接在必需参数后面」的限制了


剩余参数的处理

在ES6 中,可以使用 ...来整合或解构参数,在TypeScript 中同样可以使用 ... 的方式获取函数中的剩余参数(rest 参数)

//函数声明 ,命名函数
function add(a?: number, b: number = 132, ...args: number[]): number {
    console.log(args); //[7, 9, 6]
    return a + b
}
//函数表达式,命名函数
let sum: (a: number, b?: number, ...args: number[]) => number = function (a: number, b: number = 798, ...args: number[]): number {
    console.log(args); // [4, 7, 9, 6]
    return a + b
}
//函数表达式,回调箭头函数
let callback: (a: number, b?: number, ...args: number[]) => number = (a: number, b: number = 456, ...args: number[]): number => {
    console.log(args); //[5, 4, 7, 9, 6]
    return a + b
}

console.log(add(5, 4, 7, 9, 6));
console.log(sum(3, 5, 4, 7, 9, 6));
console.log(callback(9, 3, 5, 4, 7, 9, 6));

事实上,args 是一个数组。所以我们可以用数组的类型来定义它:

注意... 整合参数只能是最后一个参数。


函数重载

定义了一个 add 函数,希望可以对字符串和数字类型进行相加:

function add(a1: number | string, a2: number | string) {
    return a1 + a2; // 报错
  }
  
  // 方式一:联合类型
  function add(a1: number | string, a2: number | string) {
    if (typeof a1 === "number" && typeof a2 === "number") {
      return a1 + a2;
    } else if (typeof a1 === "string" && typeof a2 === "string") {
      return a1 + a2;
    }
  }
  
//   add(10, 20);
  /**
   * 通过联合类型有两个缺点:
   *  1.进行很多的逻辑判断(类型缩小)
   *  2.返回值的类型依然是不能确定
   *  3.返回值不能够精确的表达,输入为数字的时候,输出也应该为数字,输入为字符串的时候,输出也应该为字符串。
   */
  
  // 解决方式二:函数重载 函数的名称相同, 但是形参不同的多个函数, 就是函数的重载
  // 我们可以去编写不同的重载签名(overload signatures)来表示函数可以以不同的方式进行调用
  // 一般是编写两个或者以上的重载签名,再去编写一个通用的函数实现
  function add(num1: number, num2: number): number; // 没函数体
  function add(num1: string, num2: string): string;
  
  // 具体实现函数,不能直接调用来处理逻辑哦
  function add(num1: any, num2: any): any {
    if (typeof num1 === "string" && typeof num2 === "string") {
      return num1.length + num2.length;
    }
    return num1 + num2;
  }
  
  const result1 = add(20, 30);
  const result2 = add("abc", "cba");
  console.log(result1);
  console.log(result2);

函数的 Void 类型

Void 类型 表示无返回值
概念:JS中的有些函数只有功能没有返回值,此时使用void进行返回值注解,明确表示函数没有函数值

注意事项: :在JS中如何没有返回值,默认返回的是undefined,在TS中 void和undefined不是一回事,undefined在TS中是一种明确的简单类型,如果指定返回值为undefined,那返回值必须是undefined类型

void 返回值类型,约束了,函数不能返回 “有效值” ,可以返回 null,undefined,或者 只有 return 关键字,更甚至,return 关键字都可以不需要存在。就是不能返回 任何 有效值

function fn(): void {
    // return null
    // return undefined
    return
}

函数的 never 类型

与 Void 类型类似,不过比 Void 类型,更加的绝对化,函数体中,连 return 关键字都不能出现,一但出现 return 关键字,不论有没有返回有效值,就会报错。所以说从某种意义上来说。never 类型 是 void 类型的 升级严格模式版

function fn():never{
    throw new Error('终止')
}

本章节,主要给大家介绍了,在TypeScript 中,围绕着函数,来对函数做一系列的,类型约束的使用讲解。


🚵‍♂️ 博主座右铭:向阳而生,我还在路上!
——————————————————————————————
🚴博主想说:将持续性为社区输出自己的资源,同时也见证自己的进步!
——————————————————————————————
🤼‍♂️ 如果都看到这了,博主希望留下你的足迹!【📂收藏!👍点赞!✍️评论!】
——————————————————————————————

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/687294.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

电力载波远程控制系统

随着电力技术的不断发展,电力载波远程控制系统成为了现代电力系统中的重要组成部分。电力载波远程控制系统是一种利用电力载波技术实现远程控制的系统,可以对电力系统中的各种设备进行实时监测、控制和管理,提高电力系统的安全性、可靠性和效…

Efficient Video Transformers with Spatial-Temporal Token Selection阅读笔记

摘要 Video Transformers在主要视频识别基准测试中取得了令人印象深刻的结果,但其计算成本很高。 在本文中,我们提出了 STTS,这是一种令牌选择框架,它根据输入视频样本在时间和空间维度上动态选择一些信息丰富的令牌。 具体来说&…

Qt/C++编写视频监控系统78-视频推流到流媒体服务器

一、前言 视频推流作为独立的模块,目前并没有集成到视频监控系统中,目前是可以搭配监控系统一起使用,一般是将添加好的摄像头通道视频流地址打开后,读取视频流重新推到流媒体服务器,然后第三方可以从流媒体服务器拉取…

博世中国×牛客:精准人才简历增长100%!智能制造大揭秘

当一家智能制造巨头,在面向人工物联网企业的全面转型中,人才需求发生变化,年轻的校园顶尖科技人才成为刚需。 此时,内部需求激增,人才要求高还翻倍增长,但外部供需失衡,人才供给极少。尽管已然…

编译原理二:有限状态机

文章目录 1. 有限状态机介绍1.1. 确定性有限状态机(DFA)1.2. 非确定性有限状态机(NFA)1.3. 有限状态机的应用 2. 例子:实现一个简易版本的分词 1. 有限状态机介绍 有限状态机是一种计算模型,它可以接受一串…

脑机接口科普0023——黑门03:伦理道德中的电车难题

本文禁止转载!!!!! 脑机接口科普0022——黑门02:伦理道德问题_sgmcy的博客-CSDN博客 前文中,罗列了一下脑机接口这个技术中,会遇到哪些伦理道德的问题。 前文末,以黑门…

Stable Diffusion 对图像进行风格化

风格化是基于现有图像转换成另一种风格的操作方法,通常应用于img2img中,将文字提示中特定的新风格应用于原图像上进行修改。在这个过程中并非使用随机的潜在状态,而是采用原始图像去编码初始潜在状态。在此基础上通过加入少量的随机性&#x…

【观察】新华三:数据中心可组合架构创新,提供多元算力的“最优解”

今天,以ChatGPT为代表的AIGC大模型,已经在国内形成了“海啸效应”,几乎所有的科技公司都在想方设法进入大模型的赛道。背后的核心驱动力,就在于大模型的最大价值在于普遍提升个人生产力,而各行各业的公司都在积极寻找应…

linux下照片添加水印乱码

java程序给图片添加中文文字水印显示乱码 原因:linux服务器没有对应的文字 解决步骤 在windows系统下文字中选一个文字(微软雅黑) windows文字保存路径:C:\Windows\Fonts 上传到linux服务器:/usr/share/fonts 新建…

Revit做基坑放坡开挖方法及快速生成基坑

一、Revit做基坑放坡开挖方法 1、建立基坑顶与基坑底轮廓参照线,使用地形表面工具通过放置点创建原始平整场地过后的地形(有坐标点可以直接导入)。 2、修改原始地形名称为:开挖前,阶段化:现有类型。 3、使用平整区域,弹…

video-从入门到精通-不管任何项目奇葩需求,这一专栏就够了

在日常我们的开发中,我们会遇到类似这样的功能,视频播放了这种情况,但是如果只是简单的实现的话,ui不满意,因为,别人有的,就是代表这是能实现的,你必须完成(苦der程序员&…

享趣闻 | 神秘感十足的5个博物馆,其中一个还是在水上?

大家好,此po是乐于分享的建模助手。 小编发现,在日常的推文里,除了BIM插件相关的推送深受各位喜爱之外,一些建筑行业相关的文章热度也蛮高的。 那本期咱们就来聊聊博物馆。 博物馆是一个能直接感受历史和文明的地方,一…

ATX Server2-多设备集群环境搭建

一、简介 ATX Server2是⼀个移动设备管理平台,主要是Python3NodeJSRethinkDB开发。用于集中管理我们的设备,以及远程运行测试用例。 官方文档:https://github.com/openatx/atxserver2 搭建这样⼀套系统,需要: 1、at…

高通工具QXDM的使用

目录 1.什么是QXDM 2.QXDM抓取log的步骤 1.将手机连接在电脑上 2.进行Connect 3.Connect后就能够抓取log 4.断开连接 5.保存log文件 1.什么是QXDM QXDM,the qualcomm extensible diagnostic monitor:高通可扩展诊断监视器 是高通公司&#xff0…

【Spring Clound】Nacos高可用集群搭建与使用

文章目录 一、Nacos 简介二、Nacos 安装2.1、Nacos 环境依赖2.2、Nacos 服务端安装 三、Nacos 部署3.1、单实例部署3.2、 集群部署3.2.1、集群架构3.2.2、模拟部署 四、微服务集成Nacos4.1、依赖组件版本选型4.2、注册中心4.2.1、服务提供者4.2.2、服务消费者4.2.3、服务调用4.…

智慧园区综合能源监测解决方案

随着能源消耗的日益增长和能源环境的日益严峻,智慧园区综合能源监测解决方案成为了当前能源管理的热点话题。智慧园区综合能源监测解决方案是一种集成化的能源监测平台,可以实现对园区内各种能源的实时监测、分析和管理,从而达到优化能源配置…

应聘软件测试,差点栽在了...这5道S级的测试用例设计题上...

1、 用例设计:根据下面需求,进行测试用例设计,请注意对测试点的表达。 (网页端)需求描述: 某项目的营养素配置页面,供用户用来配置营养素的相关信息,其中: l 项目可供用…

【嵌入式Qt开发入门】在Ubuntu下编写C++

在 Ubuntu 上面编写 C,本文内容主要介绍在 Ubuntu 在终端窗口下使用 vi/vim 编辑一 个 C源文件。通过编写最简单的示例“Hello,World!”。带领大家学习如何在 Ubuntu 终端下编辑和编译 C。这里要求大家会在 Ubuntu 上使用 vi/vim,也就是要求大…

小米的故事:创新如何将一家公司从死亡漩涡中拯救出来

小米通过在爆品体系打造、贴地的新媒体策略及小米之家新零售模式上的努力,成功地克服了低潮,在经历了两年的震荡后,在软件、硬件和新零售的增长飞轮上实现了新的外延,并在2015年至2021年期间持续增长。小米的多元化爆品和创新的零…

【pytest学习总结2】 - 如何调用pytest?

目录 2.1 如何调用pytest 2.1.1 指定要运行的测试 2.1.2 获取关于版本、选项名称、环境变量的帮助 2.1.3 分析测试的执行的持续时间 2.1.4 管理插件的加载 2.1.5 其他调用pytest的方法 🎁更多干货 完整版文档下载方式: 2.1 如何调用pytest 通常…