在这一节,我们将介绍TypeScript中的类型推断。我们将会讨论类型推断需要在何处用到以及如何推断。

基础

在TypeScript中,在几个没有明确指定类型注释的地方将会使用类型推断来提供类型信息。

var x = 3;

变量"x"的值被推断为number。这种推断发生在变量或者成员初始化、设置参数默认值、决定函数返回类型的时候。

最佳公共类型

当需要从多个表达式中进行类型推断的时候,这些表达式的类型将会用来推断出一个"最佳公共类型"。例如:

var x = [0, 1, null];

要想推断出什么例子中"x"的类型,我们需要考虑每个数组元素的类型。这里,我们给出了两个数组类型的选择:number和null。最佳公共类型算法要求考虑到所有候选的类型,并选择出与所有候选类型兼容的类型。(这里的类型可为Array<number>)

由于最佳公共类型是从提供的候选类型中选择的,有些情况下,候选类型共享一个共同类型,但没有任何一个类型是所有候选类型的父类型。例如:

class Animal {
name:string;
constructor(theName: string) { this.name = theName; }
}
class Snake extends Animal{
constructor(name: string) { super(name); }
}
class Elephant extends Animal{
constructor(name: string) { super(name); }
}
class Rhino extends Animal {
constructor(name: string) { super(name); }
}
var zoo = [new Rhino(), new Elephant(), new Snake()]; // 这里三个成员的类型分别为:Rhino、Elephant、Snake 他们是最佳公共类型的候选类型,Animal是他们的super type(译为父类型)

理想情况下,我们可能希望zoo被推断为Animal[]类型,但是因为数组中没有任何对象是严格的Animal类型,我们便不能做出推断。为了解决这个问题,当不能推断出所有候选类型的父类型的时候,我们需要明确的提供类型。

var zoo: Animal[] = [new Rhino(), new Elephant(), new Snake()];

当没有最佳公共类型的时候,推断的结果是产生一个空对象,{}。因为这个类型不含任何成员,对于其任何属性的访问都会导致错误。这种结果依然允许我们在忽略类型的方式中使用对象,但在保障类型安全的前提下,该对象的类型不能被隐式的确定。

上下文(语境)类型

在TypeScript中,类型推断在某些情况下也存在于"其他方面"。这被称为"上下文归类"。上下文归类发生在当一个表达式的类型在其所在的上下文中被隐式的指定的时候。例如:

window.onmousedown = function(mouseEvent) {
console.log(mouseEvent.buton); //<- 编译时抛出错误
};

上面的代码将会给出一个类型错误,TypeScript的类型检查器使用Window.onmousedown函数的类型来推断右边的函数表达式类型。当它这么做的时候,便能够推断出参数mouseEvent的类型。 如果这个表达式不在可进行上下文归类的位置,参数mouseEvent 需要给定一个any类型,这样就不会出现错误了。

如果需要上下文归类的表达式内容中包含明确的类型信息,则会忽略上下文归类。我们重写上面的例子:

window.onmousedown = function(mouseEvent: any) {
console.log(mouseEvent.buton); //<- 现在不会报错了
};

参数明确指定类型的函数表达式将会忽略上下文归类。经过这样的处理就不会报错了,因为没有应用到上下文归类。

上下文归类可应用于许多场景。常见的场景包括函数调用的参数、赋值的等号右边表达式、类型确定、对象成员和数组字面量、返回值语句。上下文类型也作为最佳公共类型的候选类型。例如:

function createZoo(): Animal[] {
return [new Rhino(), new Elephant(), new Snake()];
}

在这个例子中,最佳公共类型有四个候选类型:Animal,Rhino,Elephant,和Snake。其中,Animal可以作为最佳公共类型。

形式有点像数学中的求最小公倍数...

TypeScript Type Innference(类型推断)的更多相关文章

  1. TypeScript Type Compatibility(类型兼容)

    TypeScript中的类型兼容是基于结构归类的.在普通分类的相比之下,结构归类是一种纯粹用于将其成员的类型进行关联的方法.思考下面的代码: interface Named { name: strin ...

  2. Java Type Inference (类型推断)

    public class Test2 { public static void main(String[] args) { ArrayList<String> list = newArra ...

  3. 聊聊 TypeScript 中的类型保护

    聊聊 TypeScript 中的类型保护 在 TypeScript 中使用联合类型时,往往会碰到这种尴尬的情况: interface Bird { // 独有方法 fly(); // 共有方法 lay ...

  4. 现代C++之理解模板类型推断(template type deduction)

    理解模板类型推断(template type deduction) 我们往往不能理解一个复杂的系统是如何运作的,但是却知道这个系统能够做什么.C++的模板类型推断便是如此,把参数传递到模板函数往往能让 ...

  5. [Effective Modern C++] Item 2. Understand auto type deduction - 了解auto类型推断

    条款二 了解auto类型推断 基础知识 除了一处例外,auto的类型推断与template一样.存在一个直接的从template类型推断到auto类型推断的映射 三类情况下的推断如下所示: // ca ...

  6. [Effective Modern C++] Item 1. Understand template type deduction - 了解模板类型推断

    条款一 了解模板类型推断 基本情况 首先定义函数模板和函数调用的形式如下,在编译期间,编译器推断T和ParamType的类型,两者基本不相同,因为ParamType常常包含const.引用等修饰符 t ...

  7. 为vue3.0学点typescript, 解读高级类型

    知识点摘要 本节课主要关键词为: 自动类型推断 / 类型断言 / 类型别名(type) / 映射类型(Pick/Record等...) / 条件类型(extends) / 类型推断(infer) 自动 ...

  8. C#的类型推断发展史

    前言:随着C#的版本升级,C#编译器的类型推断功能也在不断的升级以适应语言进化过程中的变化,并为这个过程做了相应的优化. 隐式类型的数组 在C#1和C#2中,作为变量声明和初始化的一部分,初始化数组的 ...

  9. jdk8系列二、jdk8方法引用、重复注解、更好的类型推断、新增注解

    一.方法引用 方法引用使得开发者可以直接引用现存的方法.Java类的构造方法或者实例对象.方法引用和Lambda表达式配合使用,使得java类的构造方法看起来紧凑而简洁,没有很多复杂的模板代码. 方法 ...

随机推荐

  1. Play Framework 完整实现一个APP(七)

    1.添加验证码 Application Controller添加captcha() public static void captcha() { Images.Captcha captcha = Im ...

  2. SqlServer环境配置和卸载

    一.数据库简介 SQLServer环境配置 安装好数据库以后怎么启用sa账号,来访问数据库. 1.先用windows账号登录数据库. 2.启用windows身份验证方式和sql server身份验证方 ...

  3. ORA-27125: unable to create shared memory segment

    平台环境   :  Oracle Linux Server release 5.7 x86_64 数据库版本 :  Oracle Database 10g Enterprise Edition Rel ...

  4. [翻译]当分发数据库增长到25G时如何解决

    有时候,分发数据库(Distribution Database)会增长得非常大,那么如何解决呢,请看Chris Skorlinski,  Microsoft SQL Server Escalation ...

  5. WinForm:DataGridViewButtonColumn的使用

    1. 添加 DataGridViewButtonColumn DataGridViewButtonColumn dgv_button_col = new DataGridViewButtonColum ...

  6. Mongodb基本数据类型、常用命令之增加、更新、删除

    1.null---表示空值或者该字段不存在,如{"name":null} 2.布尔 --- 和java中的布尔一样,有两种:true,false,如{"sex" ...

  7. 解决MyEclipse中的js报错的小方法

    今天,下了个模版,但是导进去的时候发现js会报错.看了下其他都没有错误.而有一个js报错误,请原谅我有点红色强迫症,不能留一点红色 . 错误如下:Syntax error on token " ...

  8. 【小白的CFD之旅】11 敲门实例【续】

    主要内容: 接上文[小白的CFD之旅]10 敲门实例 2.4 Materials设置2.5 Cell Zone Conditions2.6 Boundary Conditons2.7 Dynamic ...

  9. POJ3398Perfect Service[树形DP 树的最大独立集变形]

    Perfect Service Time Limit: 2000MS   Memory Limit: 65536K Total Submissions: 1518   Accepted: 733 De ...

  10. Java程序设计之线程池应用

    这里简单说一个线程池的小应用,从控制台输入线程访问的线程数量,输出输出工作的线程名,之前先构造一个包含了5条线程的对象. 代码: import java.util.Scanner; import ja ...