面向对象OOP

这是我参与更文挑战的第17天,活动详情查看: 更文挑战

面向对象,Object Oriented Programming,所以也叫做OOP。
随着计算机技术的发展,要处理的计算机问题越来越复杂。为了更好的解决这样的问题,就出现了一切皆对象的面向对象编程。
以下将从this,闭包,原型,构造函数,封装,继承,多态,这几个方面进行展开。

this

大多数时候,this代表函数调用的上下文。

this-全局上下文/严格模式

  • 不要开启严格模式

  • 但永远当成自己在严格模式下开发

  • 不要使用全局上下文

this-局部上下文

普通函数调用构造函数
getter/setter

const mike = {
    name: 'Mike';
    say() {
        console.log(this.name);
    }
};
mike say(); // 'Mike'

// 构造函数
function Universe() {
    this.answer = 42;
}
const world = new Universe();
console.log(world.answer); //42

//getter/setter
const fibonacci = {
    small: 0,
    big: 1,
    get next () {
        [this.small,this.big] = [this.big,this.small + this.big];
        return this.small;
    }
};
for(let i = 0;i<10; i++) {
    console.log(fibonacci.next);
}
// 1,1,2,3,5,8,13,21,34,55
复制代码

this-bind/call/apply

//实现一个bind
function bind (func, scope) {
    return (...args) => func.apply(scope,args)
}

const a = {
    answer: 37
};

function response () {
    console.log(this.answer)
}

const b = {
    answer: 42,
    response:bind(response,a)
};

b.response(); //37

// call/apply
response.call(a); //37
response.apply(a); //37
复制代码

this-arrow function

function work () {
    const todo = {
        list: ['job1','job2','job3'],
        process: () => {
            todo.list.forEach(task => {
                console.log(`${this.name} finish ${task}`);
            });
        }
    };
    todo.process();
}

const Jack = {
    name: 'Jack',
    work
};

Jack.work();
//'Jack finished job1'
//'Jack finished job2'
//'Jack finished job3'
复制代码

闭包

function drum () {
    let sound;
    return {
        dongci () {
            sound = 'dongci';
        },
        daci () {
            sound = 'daci';
        },
        hit () {
            console.log(sound);
        }
    };
}

const { dongci, daci, hit } = drum();

dongci();
hit();
daci();
hit();
// dongci daci
复制代码

原型

javascript Java
基于原型 基于类
所有对象均为实例 类和实例是不同的事物
通过构造函数定义和创建对象 通过类定义来定义类,通过构造函数来实例化类
通过new操作符创建对象 通过new操作符创建对象
指定一个对象为原型,并且以构造函数一起构造对象的层级结构 通过类定义来定义现有类的子类,从而构建对象的层级结构
遵循原型链继承属性 遵循类链继承属性
构造函数和原型指定了对象的初始属性集。允许动态向单个对象或整个对象集中添加或移除属性 类定义定义了所有实例的所有属性,无法在运行时动态添加

DEMO

function Cat (name) {
    if (name) {
        this.name = name;
    }
};

Cat.prototype.say = function () {
    console.log(this.name);
};

Cat.prototype.name = 'mimi';

const mimi = new Cat();
mimi.say(); // 'mimi'

const ketty = new Cat('Ketty');
ketty.say(); // 'Ketty'

复制代码

↓↓↓

class Cat {
    constructor(name) {
        if (name) {
            this.name = name;
        }
    }
    name = 'mimi';
    say() {
        console.log(this.name);
    }
}

const mimi = new Cat();
mimi.say(); // 'mimi'

const ketty = new Cat('Ketty');
ketty.say(); // 'Ketty'

复制代码

原型-属性查找

// 测试代码,实际代码中请勿模仿
const animal = {
    name: 'animal',
    mouth: 1,
    tail: 0
}

const dog = {
    name: 'dog',
    tail: 1
}

const labrador = {
    name: 'labrador'
}

dog.__proto__ = animal;
labrador.__proto__ = dog;

console.log(labrador.name); // 'labrador'
console.log(labrador.mouth); // 1
console.log(labrador.tail); // 1
复制代码

构造函数

构造函数-new

const dog = new Dog();
复制代码

↓↓↓

const temp = {};
temp.__proto__ = Dog.prototype;
const dog = Dog.call(temp)||temp;
复制代码

构造函数-静态方法 vs. 原型方法 vs. 实例方法

function Dog() {
    // 实例方法
    this.foo = function() {};
}

// 原型方法
Dog.prototype.bar = function() {};

// 静态方法
Dog.baz = function() {};

const dog = new Dog();
// 实例方法
dog.qux = function() {};
复制代码

↓↓↓

class Dog {
    constructor() {
        this.foo = () => {};
    }
    bar() {}
    static baz() {}
}
const dog = new Dog();
dog.quz = () => {};
复制代码

封装

封装-私有成员

function Person (name = "") {
    const privateName = name;
    this.getName = function () {
        return privateName;
    }
    this.setName = function (newName) {
        privateName = newName;
    };
}

const someone = new Person('xiaoming');
some.setName('xiaoqiang');
console.log(someone.getName());// 'xiaoqiang'
复制代码

继承

继承-es3时代

function Parent() {
    this.asserts = [];
}
function Child(){};
Child.prototype = new Parent();

const Jack = new Child();
const Mike = new Child();

Jack.asserts.push('money');
console.log(Mike.asserts); //['money']
复制代码

继承-es3时代-better

function Parent () {
    this.asserts = [];
}
function Child () {
    Parent.call(this);
}
Child.prototype = new Parent();

const Jack = new Child();
const Mike = new Child();

Jack.asserts.push('money');
console.log(Mike.asserts); //[]
复制代码

继承-es3时代-另一种思路

function create(o) {
    function F(){}
    F.prototype = o;
    return new F();
}

const parent = {
    asserts: []
}

const oneChild = create(parent);
const anotherChild = create(parent);

oneChild.asserts.push('money');
console.log(anotherChild.asserts);//['money']
复制代码

继承-es3时代-最佳实践

function create(o) {
    function F(){};
    F.prototype = o;
    return new F();
}

function inherit(superType,subType) {
    const prototype = create(superType.prototype);
    prototype.constructor = subType;
    subType.prototype = prototype;
}

function Parent() {};
function Child() {
    Parent.call(this);
}
inherit(Parent,Child);
复制代码

继承-es5

function inherit(superType,subType) {
    const prototype = Object.create(superType.prototype);
    prototype.constructor = subType;
    subType.prototype = prototype;
}

function Parent(){};
function Child() {
    Parent.call(this);
}
inherit(Parent,Child);
复制代码

继承-es6

class Parent {};
class Child extends Parent {};
复制代码

继承-多继承

class Worker {};
class Farmer {};
class MigrantWorker:public Worker,publicFarmer {};
复制代码

多态

多态-oops

class Parent {
    constructor(name) {
        this.name = name;
    }
    speak() {
        console.log(`${this.name} says something`);
    }
}

class Cild extends Parent {
    constructor(...args) {
        super(...args);
    }
    speak() {
        super.speak();
        console.log('And then,he walks away');
    }
}
复制代码
© 版权声明
THE END
喜欢就支持一下吧
点赞0 分享