一种规范的定义,行为和动作的规范,对批量方法约束
属性接口
对属性进行约束
// 当与需要对批量方法传参约束时
interface FullName {
first: string,
second: string
}
function printName(name: FullName) { console.log(name) } // 只要求需要name有first与second.可以有其他属性
printName({ second: '1', first: '2' }) // { second: '1', first: '2' } 不检查顺序
可选属性
// 可选属性
interface SelectFullName {
first: string,
second?: string // 可选
}
function printSelectName(name: SelectFullName) { console.log(name) } // 只要求需要name有first与second.可以有其他属性
printSelectName({ first: '2' }) // { first: '2' }
只读属性
一些对象属性只能在对象刚刚创建的时候修改其值
相比const, 当作变量时使用const, 而当作属性时使用readonly
interface Point {
readonly x: number;
readonly y: number;
}
额外类型检查
interface SquareConfig {
color?: string;
width?: number;
}
function createSquare(config: SquareConfig): any { return config }
// 这里color拼写成colour
// let mySquare = createSquare({ colour: "red", width: 100 }); //“colour”中不存在类型“SquareConfig”。是否要写入 color?
console.log(mySquare)
注意传入createSquare的参数拼写为colour而不是color。 在js里,这会默默地失败。ts会认为存在bug。 会经过额外属性检查,检查不到对于属性时, 会报错。
但是在接口添加属性,便不会报错
interface SquareConfig {
color?: string;
width?: number;
[propName: string]: any;
}
function createSquare(config: SquareConfig): any { return config }
// 这里color拼写成colour
let mySquare = createSquare({ colour: "red", width: 100 });
console.log(mySquare) // { colour: 'red', width: 100 }
接口实现ajax的实例
interface Config {
type: string;
url: string;
data?: string;
dataType: string;
}
function ajax(config: Config) {
var xhr = new XMLHttpRequest();
xhr.open(config.type, config.url, true)
xhr.send(config.data)
xhr.onreadystatechange = function () {
if (xhr.readyState === 4 && xhr.status === 200) {
console.log('success')
}
}
}
函数类型接口
对方法传入的参数,以及返回值进行约束 批量约束. 类似一个只有参数列表和返回值类型的函数定义
interface encrypt {
(key: string, value: string): string;
}
var md5: encrypt = function (key: string, value: string): string {
return key + value
}
// 同时也不要求属性名相同
var md5: encrypt = function (k: string, v: string): string {
return k + v
}
可索引类型接口
数组对象的接口约束(不常用)
// 数组约束
interface UserArr {
[index: number]: string
}
var userArr: UserArr = ['aaa', 'bbb']
// 对象约束
interface UserObj {
[index: string]: string
}
var userObj: UserObj = { name: '20' }
类接口
对类的约束 类似抽象类
interface Animal {
name: string;
eat(str: string): void
}
class Dog implements Animal {
name: string;
constructor(name: string) {
this.name = name
}
eat() {
console.log(this.name)
}
}
当一个类实现了一个接口时,只对其实例部分进行类型检查。 constructor存在于类的静态部分,所以不在检查的范围内。
但是可以通过定义两个接口分别限制构造函数和方法实现. 在使用一个函数来生成需要类
interface DogConstructor {
new(name: string, age: number): DogInterface;
}
interface DogInterface {
eat();
}
function createDog(cons: DogConstructor, name: string, age: number): DogInterface {
return new cons(name, age); // 这里限制了传入constructor的参数
}
class Dog implements DogInterface { // 这里限制了eat方法实现
name: string
constructor(name: string) { this.name = name }
eat() {
console.log(this.name + "eating");
}
}
let d = createDog(Dog, '旺财', 2);
console.log(d) // Dog { name: '旺财' }
d.eat() // 旺财eating
接口继承
接口可以继承一个或多个接口
类可以在实现接口的同时继承类
interface Animal {
eat(): void;
}
interface Person extends Animal {
work(): void;
}
class Man implements Person {
// 这里eat与work都需要继承
eat() { console.log('eating') }
work() { console.log('working') }
}
// 同也可以在实现接口的同时继承类
class Coder {
code(): void { console.log('coding') }
}
class TSCoder extends Coder implements Person {
// 这里eat与work都需要继承
eat() { console.log('eating') }
work() { console.log('working') }
}
同时, 接口可以继承类, 并在子类声明实现接口时也要继承接口继承的类, 否则会报错
class Animal {
public name: string;
}
interface AnimalInterface extends Animal {
eat(): void;
}
// 实现接口同时继承类
class Dog extends Animal implements AnimalInterface {
eat() { }
}
// class Cat implements AnimalInterface { // 类型 "Cat" 中缺少属性 "name",但类型 "AnimalInterface" 中需要该属性。
// eat() { }
// }
/// 或者直接再类中添加对应属性
class Cat implements AnimalInterface {
eat() { }
public name: string
}
但是当接口继承类的属性为private 和protected时. 直接再子类中声明类就不行了, 所以不推荐在子类中添加类
class Animal {
private name: string;
}
// class Cat implements AnimalInterface { // 类型具有私有属性“name”的单独声明
// eat() { }
// private name: string
// }
class Animal {
protected name: string;
}
// // 或者直接再类中添加对应属性
// class Cat implements AnimalInterface { // 属性“name”受保护,但类型“Cat”并不是从“Animal”派生的类
// eat() { }
// protected name: string
// }