类的继承(ES5)

2019-11-12  本文已影响0人  royluck

通过闭包实现类的静态变量:

var Book = (function (argument) {
    // 静态私有变量
    var bookNum = 0;
    // 静态私有方法
    function checkBook(name){}
    // 创建类
    function _book(newId, newName, newPrice){
        // 私有变量
        var name, price;
        // 私有方法
        function checkID(id){}
        // 特权方法
        this.getName = function(){};
        this.getPrice = function(){};
        this.setName = function(){};
        this.setPRice = function(){};
        // 共有属性
        this.id = newId;
        // 共有方法
        this.copy = function(){};
        bookNum++
        if(bookNum > 100){
            throw new Error('我们仅出版100本书.');
        }
        // 构造器
        this.setName(name);
        this.setPrice(price);
    }
    __book.prototype = {
        // 静态共有属性
        isJSBook: false,
        // 静态公有方法
        display: function(){}
    }
    // 返回类
    return __book;
})()

创建对象的安全模式:

var Book = function(title, time, type){
    // 判断执行过程中this是否是当前这个对象(如果是说明是用new创建的)
    if(this instanceOf Book){
        this.title = title;
        this.time = time;
        this.type = type;
    // 否则重新创建这个对象       
    }else{
        return new Book(title, time, type);
    }
}

var book = new Book('javaScript','2014','js')

类主要由三部分组成:

instanceof是判断前面的对象是否是后面类的实例;
创建的所有对象都是Object的实例。



实现继承:
function SuperClass(){
    this.superValue = true;
}

SuperClass.prototype.getSuperValue = function(){
    return this.superValue;
}

function SubClass(){
    this.subValue = false;
}

SubClass.prototype = new SubClass();

subValue.prototype.getSubValue = function(){
    return this.subValue;
};

缺点:在创建父类的时候,无法向父类传递参数,因而在实例化父类的时候也无法对父类构造函数内的属性进行初始化;


function SuperClass(id) {
    this.id = id
}

SuperClass.prototype.showBooks = funciton(){
    console.log(this.id);
}

function SubClass(id){
    SuperClass.call(this, id); // 构造函数继承精华
}

var instance1 = new SubClass(10) // =>10
instance1.showBooks()   // TypeError

缺点:没有涉及原型prototype,父类的原型方法不被子类继承。因此instance1.showBooks()报错误TypeError


function SuperClass(id){
    this.books = ['html', 'css', 'javaScript'];
    this.id = id;
}

SuperClass.prototype.showBooks = function(){
    console.log(this.books)
}

function SubClass(id){
    SuperClass.call(this, id) // 父类构造函数被调用第一次
}

SubClass.prototype = new SuperClass() // 父类构造函数被调用第二次

SubClass.prototype.showId = function () {
    console.log(this.id)
}

var instance1 = new SubClass(10)
var instance2 = new SubClass(11)
instance1.books.push('设计模式')
instance1.showBooks() //  ["html", "css", "javaScript", "设计模式"]
instance1.showId() // =>10

instance2.showBooks() //  ["html", "css", "javaScript"]
instance2.showId() // =>11

缺点:父类构造函数被调用二次


// 等于 Object.create()方法
function inheritObject (o) {
    function f () {

    }
    f.prototype = o
    return new f()
}

var book1 = {
    name: 'js book',
    alikeBook: ['css book', 'html book']
}

var book2 = inheritObject(book1)
// var book2 = Object.create(book1)
book2.name = 'flash book'
book2.alikeBook.push('as book')

var book3 = inheritObject(book1)
console.log(book1.name) // => js book
console.log(book1.alikeBook) //  => ["css book", "html book", "as book"]
console.log(book2.name) // => flash book
console.log(book2.alikeBook) // => ["css book", "html book", "as book"]
console.log(book3.name) // => js book
console.log(book3.alikeBook) // => ["css book", "html book", "as book"]

缺点:跟类式继承一样,父类对象的book中的值类型的属性被复制,引用类型的属性被共用


function createBook (obj) {
    var o = new inheritObject(obj);
    // 拓展新对象
    o.getName = function () {
        console.log(this.name)
    }
    return o
}
var book4 = createBook(book1)
console.log(book4.name) // =>js book
console.log(book4.alikeBook) // =>["css book", "html book", "as book"]
book4.getName() // =>js book
// 寄生组合式继承
function inheritPrototype (subClass, superClass) {
    var p = Object.create(superClass.prototype);
    p.constructor = subClass;
    subClass.prototype = p;
}

function SuperClass (name) {
    this.name = name;
    this.colors = ['red', 'yellow', 'blue'];
}

SuperClass.prototype.getName = function () {
    console.log(this.name)
}

function SubClass (name, time) {
    SuperClass.call(this, name);
    this.time = time;
}

inheritPrototype( SubClass, SuperClass )

// SubClass.prototype = new SuperClass()

SubClass.prototype.getTime = function () {
    console.log(this.time)
}

var instance1 = new SubClass('css book', 2014);
var instance2 = new SubClass('js book', 2019);

instance1.getTime()
instance1.getName()
instance2.getTime()
instance2.getName()

instance1.colors.push('black')
console.log(instance1.colors) // => ["red", "yellow", "blue", "black"]
console.log(instance2.colors) // => ["red", "yellow", "blue"]
上一篇 下一篇

猜你喜欢

热点阅读