js继承的实现

问题

继承有什么作用? (难度:*

  • 继承是指一个对象直接使用另一对象的属性和方法。它提高了代码的复用性,便于程序和功能的扩展,继承后的函数可以使用公有的属性和方法。

有几种常见创建对象的方式? 举例说明? (难度:**

  • 直接创建,对象字面量方法,无法传参

    1
    2
    3
    4
    5
    6
    7
    8
    var person ={
    name : 'lynn',
    age : 18,
    aboutHer : function(){
    console.log('Her name is ' + this.name + ',and she is'+this.age);
    }
    }
    person.aboutHer();//对象内部的拥有自己的属性,但如果要创建类似的方法,还是每个都要单独定义。重复造轮子。
  • 工厂模式

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    function Person(name, age){
    var obj ={
    name : name,
    age : age,
    aboutHer : function(){
    console.log('Her name is ' + this.name + ',and she is '+this.age);
    }
    }
    return obj;
    }
    var p1 = Person('lynn',18);
    var p2 = Person('mia',23);
    p1.aboutHer();/*Her name is lynn,and she is 18 这种创建对象的方式叫工厂模式*/
    p2.aboutHer();//Her name is mia,and she is 23 根据传入的信息不同,用共同的方式生成共同类型的不同信息,解决创建重复性的对象,无法得到对象的类型。
  • 构造函数模式

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    function Person(name, age){
    this.name = name;
    this.age = age;
    this.aboutHer = function(){
    console.log('Her name is ' + this.name + ',and she is '+this.age);
    }
    }
    var p1 = new Person('lynn',23);
    var p2 = new Person('mia',18);
    p1.aboutHer();/*Her name is lynn,and she is 23 这种创建对象的方式叫工厂模式*/
    p2.aboutHer();//Her name is mia,and she is 18 根据传入的信息不同,用共同的方式生成共同类型的不同信息,解决创建重复性的对象,也得到了对象的类型,但是这些对象只能有这些属性和方法都一样,无法加入自己独有的方法和属性
  • 原型方式

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    //把所有对象使用的公共资源放在原型对象。个性属性和方法放在Person函数内,这样就避免占用内存,拥有了构造函数和原型的共同优点
    function Person(name, age){
    this.name = name;
    this.age = age;
    }
    Person.prototype.aboutHer={
    relation: 'sister',
    aboutHer :function(){
    console.log('Her name is ' + this.name + ',and she is '+this.age+'.They are '+this.relation);
    }
    }
    var p1 = new Person('lynn',23);
    var p2 = new Person('mia',18);
    p2.aboutHer();//Her name is mia,and she is 18.They are sister
    `

下面两种写法有什么区别? (难度:*

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
//方法1
function People(name, sex){
this.name = name;
this.sex = sex;
this.printName = function(){
console.log(this.name);
}
}
var p1 = new People('饥人谷', 2)

//方法2
function Person(name, sex){
this.name = name;
this.sex = sex;
}

Person.prototype.printName = function(){
console.log(this.name);
}
var p1 = new Person('若愚', 27);
  • 第一种方法只是简单的构造函数方式,将属性和方法写在函数内部,需要时直接调用即可,无法实现继承和扩展。第二种将方法写在原型函数上,通过构造函数生成的对象可以调用这个公用的方法,节省了资源,同时便于扩展,实现继承

    Object.create 有什么作用?兼容性如何?如何使用? (难度:*

  • Object.create() 方法创建一个拥有指定原型和若干个指定属性的对象。
  • 兼容性:只兼容IE9+,Chrome5+,Firefox 4.0+,Opear 11.60+,Safari 5+
  • 使用:Object.create(proto, [ propertiesObject ]),将创建的原型对象赋值到新函数的原型,实现继承
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    // 初始定义
    function Person(name, sex){
    this.name = name;
    this.sex = sex;
    }
    Person.prototype.printName=function(){
    console.log("name is " + this.name + ";Gender is " + this.sex);
    }
    function Student(name, sex, grade){
    Person.call(this, name, sex);
    this.grade=grade;
    }
    // Object.creat创建法,实现创建原型对象,使Student继承Person的方法
    function inherit(superType, subType){
    var _prototype = Object.create(superType.prototype);
    _prototype.constructor = subType;//保证新原型函数的constructor指向函数本身
    subType.prototype = _prototype;
    }

    inherit(Person, Student);

    //写完原型继承后再写自己的方法
    Student.prototype.study=function () {
    console.log(this.name + " study at " + this.grade);
    }

    var s = new Student("findmoon","male","senior");
    s.printName();
    s.study();

0_1479827488301_upload-206eae35-65b7-4b3f-8f98-4eb6d1955aea

hasOwnProperty有什么作用? 如何使用? (难度:*

  • 判断一个属性是对象的自定义属性还是原型链上的属性,如果是自定义属性则返回true,否则人为false
  • 使用,例如对于上一题中的函数使用构造函数生成一个hasOwn对象并判断
    1
    2
    3
    4
    5
    6
    var hasOwn = new Student("Gloria","female","three")
    console.log(hasOwn.hasOwnProperty("name"));
    console.log(hasOwn.hasOwnProperty("sex"));
    console.log(hasOwn.hasOwnProperty("grade"));
    console.log(hasOwn.hasOwnProperty("study"));
    console.log(hasOwn.hasOwnProperty("printName"));

结果如下,并未判断原型上的属性
0_1479904978805_upload-3a4018e6-ce1a-4ac8-a436-2972a795b2d0

实现Object.create的 polyfill,如:(ps: 写个 函数create,实现 Object.create 的功能) (难度:**

  • 一个polyfill是一段代码(或者插件),提供了那些开发者们希望浏览器原生提供支持的功能,也就是当浏览器不支持某些功能时,我们使用原生的方法去进行修补,通常的做法是先检查当前浏览器是否支持某个API,如果不支持的话就加载对应的polyfill。
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    		function create(obj){
    //为了节省内存,使用一个共享的构造器
    function Temp() {}
    var newobj = (function (obj) {
    if (typeof obj != 'object') {
    throw TypeError('Object prototype may only be an Object or null');
    }

    Temp.prototype = obj;
    var prot = new Temp();
    Temp.prototype = null;
    return prot;
    })(obj);
    return newobj;
    }


    var obj = {a: 1, b:2};
    var obj2 = create(obj);
    console.log(obj2.a); //1

如下代码中call的作用是什么? (难度:**

1
2
3
4
5
6
7
8
function Person(name, sex){
this.name = name;
this.sex = sex;
}
function Male(name, sex, age){
Person.call(this, name, sex); //把this的作用域指向Person,即在Male函数下执行Person(name,sex)因此得以继承Person的name和sex属性
this.age = age;
}

补全代码,实现继承 (难度:**

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28

function Person(name, sex){
this.name = name;
this.sex = sex;
}

Person.prototype.getName = function(){
return this.name;
};

function Male(name, sex, age){
Person.call(this,name,sex);
this.age = age;
}

var _prototype = Object.create(Person.prototype);
_prototype.constructor = Male;
Male.prototype = _prototype;

Male.prototype.printName = function(){
console.log("name is " + this.name);
};
Male.prototype.getAge = function(){
return this.age;
};

var ruoyu = new Male('若愚', '男', 27);
ruoyu.printName();//name is 若愚

代码

实现如下dialog 弹窗功能, 参考效果 (难度:*

dialog预览,使用的实例中的代码,私下会抽时间自己认真写写,包括日历组件

文章目录
  1. 1. 问题
    1. 1.1. 继承有什么作用? (难度:*)
    2. 1.2. 有几种常见创建对象的方式? 举例说明? (难度:**)
    3. 1.3. 下面两种写法有什么区别? (难度:*)
    4. 1.4. Object.create 有什么作用?兼容性如何?如何使用? (难度:*)
    5. 1.5. hasOwnProperty有什么作用? 如何使用? (难度:*)
    6. 1.6. 实现Object.create的 polyfill,如:(ps: 写个 函数create,实现 Object.create 的功能) (难度:**)
    7. 1.7. 如下代码中call的作用是什么? (难度:**)
    8. 1.8. 补全代码,实现继承 (难度:**)
  2. 2. 代码
    1. 2.1. 实现如下dialog 弹窗功能, 参考效果 (难度:*)
,