编程语言分类
编程语言按照数据类型可以分成两类:静态类型语言和动态类型语言
- 静态类型语言
- 定义:编译时便已确定变量的类型
- 优点:在编译时可以发现类型不匹配的错误,编辑器可以帮我们提前避免程序在运行期间有可能发生的一些错误。在程序中明确规定了数据类型,编译器还可以针对这些信息对程序做一些优化,提高程序执行速度。
- 缺点:迫使程序员依照强契约来编写程序。类型的声明也会增加更多的代码,在编写过程中,也会让程序员的精力从思考业务逻辑上分散开来
- 动态类型语言
- 定义:变量类型要到程序原型时,被赋予某个值之后,才会具有某种类型
- 优点:编写代码少,更加简洁,开发者更专注于逻辑表达。
- 缺点:无法保证变量的类型,从而在程序的运行期间有可能发生跟类型相关的错误
多态
同一操作作用于不同的对象上面,可以产生不同的解释和不同的执行结果,换句话说,给不同的对象发送同一个消息的时候,这些对象会根据这个消息分别给出不同的反馈。最根本的作用是把过程化的条件分支语句转化为对象的多态性,从而消除这些条件分支语句。
鸭与鸡的故事
makeSound方法里面传入不同的对象,console.log得到不同的返回值。这就是多态的具体表现,不需要在makeSound做if-else类型判断。
<template>
<div>
<button @click="animalSound.makeSound(duck)">鸭子</button>
<button @click="animalSound.makeSound(chicken)">鸡</button>
</div>
</template>
<script lang="ts">
import { defineComponent } from 'vue'
import { AnimalSound, Animal } from '@/utils/polyFac';
export default defineComponent({
setup() {
return {
animalSound: new AnimalSound(),
chicken: new Animal('gegege'),
duck: new Animal('gagaga'),
}
},
})
</script>
// polyFac.js
export class AnimalSound {
makeSound(animal) {
animal.makSound()
}
}
export class Animal {
constructor(props) {
this.sound = props;
}
makSound() {
console.log(this.sound);
}
}
封装
封装的目的是将
信息隐藏,狭义上的封装指的是封装数据和封装实现。广义上来说还包含封装类型和封装变化。
封装数据
const object = (function() {
var _name = 'test'; // 私有变量private
return {
getName() { //公开变量 public
return _name
}
}
})()
console.log(object.getName()); // test
console.log(object._name); // undefined
封装实现
// $$each封装内部循环实现细节,只要对外接口没有变化,用户就不用关心内部实现的改变
Object.prototype.$$each = function(cb: Function){
for (const key in this) {
if (Object.prototype.hasOwnProperty.call(this, key)) {
cb(this[key])
}
}
};
const obj = {a: 1, b: 2};
obj.$$each((val: any) => console.log(val)) // 输出1、2
封装类型
- 封装类型是静态类型语言中一种重要的封装方式,一般来说是通过抽象类和接口来进行额,但是在JS中没有相关支持,所以对于JS的设计模式来说,是不需要过分区分类型的。
封装变化
- 从设计模式的角度出发,封装更重要体现在封装变化,设计模式基本上可以被划分为
创建型模式、结构型模式和行为型模式。 - 通过封装变化的方式,将系统中稳定不变的部分和容易变化的部分分隔开来,从而最大程度的保证程序的稳定性和扩展性。这些后续会深入学习。