1.TypeScript-Basic
2.TypeScript interface
3.Typescript-module(1)
4.TypeScript Modules(2)
5.Typescript tsconfig
6.TypeScript Functions
7.Typescript Classjavascript
今天来讲说接口,首先说明若是你是java程序员,请必定忘记interface,此处的接口和彼处接口彻底不是一个思想。java
首先来一个最简单的接口
字面量接口git
不使用interface关键字就定义了一个接口程序员
function printLabel(labelledObj: {label: string}) { console.log(labelledObj.label); } var myObj = {size: 10, label: "Size 10 Object"}; printLabel(myObj);
上面没有interface关键字,哪一个是接口呢?
{label: string}
你说这个玩意不是变量labelledObj的类型吗?我知道typescript说白了就是js的类型系统,前面也介绍了如:Boolean,Number,String,Array,Enum,Any,Void
其实接口就是定义了一个对象有哪些属性,而且属性值是什么类型typescript
好了,来个高级点的(interface关键词上场)segmentfault
interface LabelledValue { label: string; } function printLabel(labelledObj: LabelledValue) { console.log(labelledObj.label); } let myObj = {size: 10, label: "Size 10 Object"}; printLabel(myObj);
OK,懂了吗,自定义类型
啊,太棒了,之后不再用判断某个属性是否un数组
interface SquareConfig { color?: string; width?: number; } function createSquare(config: SquareConfig): {color: string; area: number} { let newSquare = {color: "white", area: 100}; if (config.color) { newSquare.color = config.color; } if (config.width) { newSquare.area = config.width * config.width; } return newSquare; } let mySquare = createSquare({color: "black"});
好处:ide
预约义属性函数
编译器能够捕获对不存在属性引用的错误this
interface SquareConfig { color?: string; width?: number; } function createSquare(config: SquareConfig): { color: string; area: number } { let newSquare = {color: "white", area: 100}; if (config.color) { // Error: Property 'collor' does not exist on type 'SquareConfig' newSquare.color = config.collor; // Type-checker can catch the mistyped name here } if (config.width) { newSquare.area = config.width * config.width; } return newSquare; } let mySquare = createSquare({color: "black"});
对于这个错误例子,咱们引出了下一节
上面的例子也许有人会争辩(js的忠实用户者),js对象是灵活的,你如今搞得跟JAVA同样了!
反对~反对!
是的,typescript对对象字面量会特殊对待(即通过额外属性检查),当将他们赋值给变量或做为函数参数时。
所以你会获得一个错误
// error: 'colour' not expected in type 'SquareConfig' let mySquare = createSquare({ colour: "red", width: 100 });
解决办法
1.类型断言法(相似于c语言的强制类型转换,告诉编译器,我就要转,别给我报错啊!)
let mySquare = createSquare({ colour: "red", width: 100 } as SquareConfig);
2.钻空子法(咱们了解编译器的检查方式了,我绕过去就好了)
let squareOptions = { colour: "red", width: 100 }; let mySquare = createSquare(squareOptions);
首先咱们要确定interface使咱们定义了各类对象外形。
如今咱们把string,number,boolean,object类型都定义了,完工了!
且慢,等等~对于其余语言是够了,但js~~~
你想,js的函数是一等公民,你能忘了它~
当当当当,来了!
interface SearchFunc { (source: string, subString: string): boolean; }
demo:
let mySearch: SearchFunc; mySearch = function(source: string, subString: string) { let result = source.search(subString); if (result == -1) { return false; } else { return true; } }
好处:
1.检查参数类型
2.返回值类型检查,上例,若是你返回字符串或数字,就报错了
数组能够想象成一种特殊函数,只有一个参数(index)的函数
interface StringArray { [index: number]: string; } let myArray: StringArray; myArray = ["Bob", "Fred"];
OK,没有问题吗?index只能是number类型吗?我还知道一种叫关联数组的玩意(index是string)
咱们常常这样用obj.property和obj["property"]
目前支持两种index类型:number,string
能够同时使用两种索引类型
限制:数字索引返回值的类型必须是字符串索引返回值的类型的子类型
demo
interface NumberDictionary { [index: string]: number; length: number; // 能够,length是number类型 name: string // 错误,`name`的类型不是索引类型的子类型 }
与C#或Java里接口的基本做用同样,TypeScript也可以用它来明确的强制一个类去符合某种契约。
interface ClockInterface { currentTime: Date; } class Clock implements ClockInterface { currentTime: Date; constructor(h: number, m: number) { } }
interface ClockInterface { currentTime: Date; setTime(d: Date); } class Clock implements ClockInterface { currentTime: Date; setTime(d: Date) { this.currentTime = d; } constructor(h: number, m: number) { } }
接口描述了类的公共部分,而不是公共和私有两部分。 它不会帮你检查类是否具备某些私有成员。
这部分比较冷~
类是具备两个类型的:静态部分的类型和实例的类型
构造函数是静态部分,而一个类去实现一个带有构造器签名的接口时会报错
interface ClockConstructor { new (hour: number, minute: number); } class Clock implements ClockConstructor { currentTime: Date; constructor(h: number, m: number) { } }
那如何才能使用接口对构造器类型检查呢
interface ClockConstructor { new (hour: number, minute: number): ClockInterface; } interface ClockInterface { tick(); } function createClock(ctor: ClockConstructor, hour: number, minute: number): ClockInterface { return new ctor(hour, minute); } class DigitalClock implements ClockInterface { constructor(h: number, m: number) { } tick() { console.log("beep beep"); } } class AnalogClock implements ClockInterface { constructor(h: number, m: number) { } tick() { console.log("tick tock"); } } let digital = createClock(DigitalClock, 12, 17); let analog = createClock(AnalogClock, 7, 32);
和类同样,接口也能够相互扩展。 这让咱们可以从一个接口里复制成员到另外一个接口里,能够更灵活地将接口分割到可重用的模块里
interface Shape { color: string; } interface Square extends Shape { sideLength: number; } let square = <Square>{}; square.color = "blue"; square.sideLength = 10;
多继承
interface Shape { color: string; } interface PenStroke { penWidth: number; } interface Square extends Shape, PenStroke { sideLength: number; } let square = <Square>{}; square.color = "blue"; square.sideLength = 10; square.penWidth = 5.0;
仍是JS的特殊语法
function demo(){ ... } demo.attr1 = '1'; demo.fun = function(){ ... }
这是什么状况,函数类型,对象类型,额,混合类型
interface Counter { (start: number): string; interval: number; reset(): void; } function getCounter(): Counter { let counter = <Counter>function (start: number) { }; counter.interval = 123; counter.reset = function () { }; return counter; } let c = getCounter(); c(10); c.reset(); c.interval = 5.0;
还不是很明白