类型
断言
通过类型断言这种方式可以告诉编译器,“相信我,我知道自己在干什么”。
类型断言好比其它语言里的类型转换,但是不进行特殊的数据检查和解构。 它没有运行时的影响,只是在编译阶段起作用
// 方式一
let someValue: any = "this is a string";
let strLength: number = (<string>someValue).length;
// 方式二:as语法
let someValue: any = "this is a string";
let strLength: number = (someValue as string).length;
基本类型
let name: string = "bob";
let decLiteral: number = 6;
数组
let list: number[] = [1, 2, 3];
let list: Array<number> = [1, 2, 3];
TypeScript具有ReadonlyArray<T>类型,它与Array<T>相似,只是把所有可变方法去掉了,因此可以确保数组创建后再也不能被修改
let a: number[] = [1, 2, 3, 4];
let ro: ReadonlyArray<number> = a;
ro[0] = 12; // error!
ro.push(5); // error!
ro.length = 100; // error!
// 把整个ReadonlyArray赋值到一个普通数组也是不可以的
a = ro; // error!
// 可以用类型断言重写
a = ro as number[];
元组
元组类型允许表示一个已知元素数量和类型的数组,各元素的类型不必相同。
// 定义 a tuple type
let x: [string, number];
// Initialize it
x = ['hello', 10]; // OK
// Initialize it incorrectly
x = [10, 'hello']; // Error
// 使用
console.log(x[0].substr(1)); // OK
console.log(x[1].substr(1)); // Error, 'number' does not have 'substr'
枚举
enum类型是对JavaScript标准数据类型的一个补充。 像C#等其它语言一样,使用枚举类型可以为一组数值赋予友好的名字。(反向映射)
enum Color {Red, Green, Blue}
let c: Color = Color.Green;
默认情况下,从0开始为元素编号。你也可以手动的指定成员的数值
enum Color {Red = 1, Green, Blue}
let c: Color = Color.Green;
枚举类型提供的一个便利是你可以由枚举的值得到它的名字。
enum Color {Red = 1, Green, Blue}
let colorName: string = Color[2];
console.log(colorName); // 显示'Green'因为上面代码里它的值是2
Any
我们会想要为那些在编程阶段还不清楚类型的变量指定一个类型。 这些值可能来自于动态的内容,比如来自用户输入或第三方代码库。 这种情况下,我们不希望类型检查器对这些值进行检查而是直接让它们通过编译阶段的检查。 那么我们可以使用 any类型来标记这些变量。
let notSure: any = 4;
notSure = "maybe a string instead";
notSure = false; // okay, definitely a boolean
在对现有代码进行改写的时候,any类型是十分有用的。
Object有相似的作用,但是 Object类型的变量只是允许你给它赋任意值,却不能够在它上面调用任意的方法,即便它真的有这些方法
let notSure: any = 4;
notSure.ifItExists(); // okay, ifItExists might exist at runtime
notSure.toFixed(); // okay, toFixed exists (but the compiler doesn't check)
let prettySure: Object = 4;
prettySure.toFixed(); // Error: Property 'toFixed' doesn't exist on type 'Object'.
Void
某种程度上来说,void类型像是与any类型相反,它表示没有任何类型
function warnUser(): void {
console.log("This is my warning message");
}
接口
意义:对值的结构进行类型检查。typeScript的核心原则之一是对值所具有的结构进行类型检查。接口的作用就是为这些类型命名和为你的代码或第三方代码定义契约
interface LabelledValue {
label: string;
}
function printLabel(labelledObj: LabelledValue) {
console.log(labelledObj.label);
}
let myObj = {size: 10, label: "Size 10 Object"};
printLabel(myObj);
只读属性
interface Point {
readonly x: number;
readonly y: number;
}
let p1: Point = { x: 10, y: 20 };
p1.x = 5; // error!
泛型?????
符号
?.
用于访问可能为 null 或 undefined 的属性或方法,以避免出现异常错误。异常会返回undefined,不会报错
??
提供备选项,前面变量为null或者undefined时,取后面的值
|| 与?? 的区别
1、||d的假值判断有:false、0、空字符串、null、undefined 等
2、?? 判断左侧操作数为null或undefined时,返回右侧操作数
??=
x ??= 5,如果x为null或者undefined时,把5赋值给x
泛型
// 定义泛型
function identity<T>(arg: T): T {
return arg;
}
// 定义泛型
function loggingIdentity<T>(arg: T[]): T[] {
console.log(arg.length); // Array has a .length, so no more error
return arg;
}
// 用法一
let output = identity<string>("myString"); // type of output will be 'string'
// 用法二:类型推论 --普遍用法
let output = identity("myString");
我们给identity添加了类型变量T。 T帮助我们捕获用户传入的类型(比如:number),之后我们就可以使用这个类型。 之后我们再次使用了 T当做返回值类型。现在我们可以知道参数类型与返回值类型是相同的了
用法见用法二的普遍用法:注意我们没必要使用尖括号(<>)来明确地传入类型;编译器可以查看myString的值,然后把T设置为它的类型。