一、ts 中接口 作用 和 类型
1. 接口的作用
接口的作用、在面向对象的编程中,接口是一种规范的定义,它定义了行为和动作的规范,在程序设计里面,接口起到了一种限制和规范的作用。接口定义了某一批类所需要遵守的规范,接口不关心这些类的内部状态数据,也不关心这些类里方法的实现细节,它只规定这批类里必须提供某些方法,提供这些方法的类就可以满足实际需要。
2. 接口的类型
typeScript 中的接口类似于 java, 同时还增加了更灵活的接口类型,包含 属性、函数、可索引 和 类 等。
二、接口类型明细
1. 属性类型的接口
a. 属性类型的接口对传入的参数进行约束验证
错误写法:
正确写法:
// 这个表示 要传入一个 必须包含label 的 json 格式的数据
function box(labelInfo: {label: string}) {
console.log(1)
}
let obj2 = {label: 'gg'}
box(obj2) // 正确写法
b. 属性类型的接口: 对批量方法进行约束
属性类型的接口: 对批量方法进行约束
错误写法:
正确写法:
interface FullName{
firstName:string; // 注意, 这里要以【;】分号结束
secondName: string;
}
function getName(name:FullName) {
// 必须传入对象 firstName secondName
console.log(`${name.firstName}${name.secondName}`)
}
// 可进行批量约束
function getInfo(info:FullName) {
// 必须传入对象 firstName secondName
console.log(`${info.firstName}${info.secondName}`) // 正确写法
}
// 正确写法
getName({ // xl
firstName: 'x',
secondName: 'l'
})
// 最正确写法
let obj = { // 传入的参数必须包含 firstName secondName
age: 20,
firstName: 'x',
secondName: 'l'
}
getName(obj) // xl
// 最正确写法
let obj2 = { // 传入的参数必须包含 firstName secondName
age: 20,
firstName: 'g',
secondName: 'g'
}
getInfo(obj2) // gg
c. 属性类型接口: 参数传值顺序可以不用相同
属性类型接口: 参数传值顺序可以和接口定义的顺序不用相同,但是一定要有接口中定义的属性,不然是会报错的。
interface FullName{
firstName:string;
secondName: string;
}
function getName(name:FullName) {
}
// 参数传值顺序可以不用相同,但是一定要有接口中定义的属性,不然是会报错的。
getName({
secondName: '壮',
firstName: '小'
})
d. 属性类型接口: 可选属性
属性类型接口: 可选属性
interface FullName{
firstName:string;
secondName?: string; // secondName? 问号表示 可选属性
}
function getName(name:FullName) {
console.log(name.firstName + name.secondName) // 小undefined
}
getName({
firstName: '小'
})
2. 函数类型接口
函数类型接口: 对方法传入的参数 及返回值进行约束, 同样可以进行批量约束\
()括号里表示是对方法传入的参数进行约束,() 括号后面的是对返回值进行约束
interface secret{
// ()括号里表示是对方法传入的参数进行约束, 括号后面的是对返回值进行约束
(key:string,value:string):string;
}
const md5:secret = function(key:string, value:string):string{
return key+value
}
const hn1:secret = function(key:string, value:string):string{
return key+'--'+value
}
// 进行批量约束
alert(md5('xiao', 'gg')) // xiaogg
alert(hn1('xiao', 'gg')) // xiao--gg
3.可索引接口
可索引接口:通常用于对 数组 和对象 的约束
a. 可索引接口:数组的约束
可索引接口:数组的约束 :
[ ] 里表示数组的索引值为 Number 类型,[ ] 后面的 string 表示数组的每一项元素都必须是 string 类型。
错误写法:
正确写法:
interface UseArr {
// [] 里表示数组的索引值为 Number 类型,[] 后面的 string 表示数组的每一项元素都必须是 string 类型。
[index:number]:string;
}
// 正确写法:
let arr2:UseArr = ['xl', 'gg']
b. 可索引接口:对象的约束
可索引接口:对象的约束
[ ] 里表示对象的索引值(也就是属性名)为 string 类型,[ ] 后面的 string 表示对象的每一项属性值都必须是 string 类型。
错误写法:
正确写法:
interface UseObj{
// [] 里表示对象的索引值为 string 类型,[] 后面的 string 表示对象的每一项属性值都必须是 string 类型。
[index:string]:string;
}
// 正确写法
let obj2:UseObj = { name: 'xl'}
4. 类类型接口
类类型接口:对类的约束, 和抽象类有点相似
通过关键字 implements 来对类进行约束
interface Animal{
// 创建的类必须要有 数据类型为 string 的 name 属性
name:string;
// 创建的类必须要有 eat 方法,eat 方法中可传入一个 数据类型为 string 的参数。void 表示 eat 方法 且没有返回值
eat(str:string):void;
}
// 通过关键字 implements 来对类进行约束
class Dog implements Animal{
name: string;
constructor(name:string) {
this.name = name;
}
eat() {
console.log(this.name + '吃东西')
}
}
let d = new Dog('小狗')
console.log(d.eat()) // 小狗吃东西
class Cat implements Animal{
name: string;
constructor(name:string) {
this.name = name;
}
eat(food:string) {
console.log(this.name +"吃"+ food )
}
}
let c = new Cat('小猫')
console.log(c.eat('老鼠')) // 小猫吃老鼠
5. 接口扩展
接口扩展:接口可以继承接口
示例一:
通过类中的类型接口的扩展(接口继承接口,它需要写全继承来的属性和方法)
interface Animal{
eat():void
}
// Person 接口继承 Animal 这个接口
interface Person extends Animal {
work():void
}
class Web implements Animal{
name:string;
constructor(name:string) {
this.name = name;
}
// 通过类中的类型接口的扩展(接口继承接口,它需要写全继承来的属性和方法)
eat() {
console.log(this.name + '吃东西')
}
work() {
console.log(this.name + '在工作')
}
}
let w = new Web('果果')
w.eat() // 果果吃东西
w.work() // 果果在工作
示例二:
接口可以继承接口,并且可以继承父类
interface Animal{
eat():void;
}
interface Person extends Animal{
work():void;
}
class Program {
name:string;
constructor(name:string) {
this.name = name;
}
codeing(doing:string) {
console.log(this.name + doing)
}
}
// 这个表示继承了父类Program 并且是遵循 Person 这个接口来定义类的
class Web extends Program implements Person{
constructor(name:string) {
super(name)
}
eat() {
console.log(this.name + 'eat')
}
work() {
console.log(this.name + 'work')
}
}
let w = new Web('果果')
w.eat() // 果果eat
w.work() // 果果work
w.codeing('玩') // 果果玩