JavaScript

JavaScript - 面向对象编程二

2017-02-25  本文已影响24人  西巴撸

上次说到了构造函数的注意事项 ! 接下来是构造函数的原型对象

构造函数的原型对象

原型对象是什么?

原型对象的作用是什么?

如何访问构造函数的原型对象

构造函数.protoType

如何为构造函数的原型对象添加属性和方法

    //1. 提供构造函数
    function Student(number,name,age) {

        //1.1 设置对象的属性
        this.number = number;
        this.name = name;
        this.age = age;

        //1.2 设置对象的方法
        this.read = function () {
            console.log("阅读");
        }
    }

    //2. 使用构造函数来创建对象
    var stu1 = new Student("20160201","严雯",18);
    var stu2 = new Student("20160202","严二雯",16);

    //3. 设置构造函数的原型
    //3.1 为构造函数的原型对象添加属性
    Student.prototype.className = "神仙特技1班";

    //3.2 为构造函数的原型对象添加方法
    Student.prototype.description = function () {
        console.log("我的名字是" + this.name + "学号是" + this.number + "班级是" + this.className);
    };

    //4. 尝试访问
    console.log(stu1.className);
    console.log(stu2.className);
    stu1.description();
    stu2.description();
    /*
    原型属性和原型方法|实例属性和实例方法
    在构造函数内部设置的属性 => 实例属性
    在构造函数内部设置的方法 => 实例方法
    在构造函数的原型对象上设置的属性 => 原型属性
    在构造函数的原型对象上设置的方法 => 原型方法
    
    如果实例属性(方法)和原型属性(方法)存在同名,那么对象在使用属性(方法)的时候,访问的是
    实例属性(方法)还是原型属性(方法)?
    说明:使用构造函数创建的对象在访问属性或调用方法的时候:
    首先在内部查找有没有对应的实例属性(方法)
    如果有,那么就直接使用,如果没有找到,那么就继续去构造函数的原型中查找
    原型对象中如果存在该属性或方法,那么就直接使用,如果不存在指定的属性则返回undefined,如果不存在指定的方法则报错
    
    注意点
    通常在创建对象之前设置构造函数的原型对象(提供共享的属性|方法)
    访问原型对象的正确方法是 构造函数.protoType 而不是 对象.protoType
    */

使用原型解决构造函数创建对象的问题

//1. 提供构造函数
    function Student(number,name,age) {
        this.number = number;
        this.name = name;
        this.age = age;
    }

    //2. 设置构造函数的原型方法
    Student.prototype.description = function () {
        console.log("我的名字是" + this.name + "学号是" + this.number + "年龄是" + this.age);
    };

    //3. 使用构造函数来创建对象
    var stu1 = new Student("20170201","严雯",18);
    var stu2 = new Student("20170202","严二雯",16);

    //4. 调用创建该对象的构造函数的原型对象中的方法(检查原型方法)
    stu1.description();
    stu2.description();

    //5. 验证构造函数创建出来的多个对象共享原型对象的属性和方法
    console.log(stu1.description == stu2.description);

实例化对象和实例

    //1. 提供一个构造函数
    function Person() {

    }

    //2. 根据该构造函数创建对象 == 使用Person构造函数实例化对象
    var p1 = new Person();

    //p1 是构造函数Person的一个实例

原型的使用方法

function Person(){
        this.name = "默认的名称";
    }

    //设置原型对象
    //成员= 属性|方法
    //1. 增加成员
    Person.prototype.des = "我是直立行走的人";
    Person.prototype.logName = function(){
        console.log(this.name);
    }

    //2. 修改成员
    Person.prototype.des = "我是直立行走的人++++";
    //console.log(Person.prototype);

    var p1 = new Person();
    console.log(p1.des);
    p1.logName();

    //3. 删除成员
    //delete关键字
    //语法  delete 对象.属性
    //不能用这种方式删除原型对象上面的属性(删除的是自己的属性)
    //console.log(delete p1.des);  
    // 只能通过这种方式删除
    delete Person.prototype.des ;
    console.log(p1.des);

1.实例属性
2.实例方法

1.原型属性
2.原型方法

1.如果是替换了原型对象,那么在替换之前创建的对象和替换之后创建的对象她们指向的原型对象并不是同一个
2.构造器属性
在替换之后创建的对象中,它的构造器属性指向的不是Person构造函数,而是Object的原型对象的构造器属性

function Person(){
        this.age = 40;
    }
    var p1 = new Person();

    //var obj = new Object();
    Person.prototype = {
        // 注意:如果替换了原型对象,那么需要在原型对象中修正构造器属性
        constructor:Person,
        sayHi:function (){
            console.log("hi");
        }
    };
    var p2 = new Person();
    //p2.constructor = Person;   //在p2对象上添加了一个属性(constructor)

    //var p3 = new Person();


    //构造器属性
    console.log(p1.constructor == p2.constructor);  //false
//    console.log(p1.constructor);    //Person
//    console.log(p2.constructor);    //Object
//    console.log(p2.constructor == p2.__proto__.constructor);
//    console.log(p2.constructor == Object.prototype.constructor);

    console.log(p2);

构造器

使用原型对象的注意事项

1.对象.属性
2.构造函数.prototype.属性

1.就近原则,在访问属性的时候,先在对象自身查找(实例属性|方法),如果找到那么就直接使用
2.如果没有找到,那么就去它的原型对象身上查找,如果找到那么就使用,找不到则undefined或者是报错

1.如果是左值,那么在设置对象的属性的时候,不会去原型对象上面去找(查找自己是否有,如果有就是修改,没有就是添加)
2.如果是右值,那么在读取值的时候,先查找自己,如果找不到,再去原型身上找

1.只能通过构造函数.prototype.属性或者是直接替换原型对象的方式来设置
2.如果原型对象的属性是引用类型的,那么可以通过对象的方式来进行设置

function Person(){
        this.des = "默认的描述信息"
    }
    Person.prototype = {
        constructor:Person,
        des :"描述信息",
        logDes:function (){
            console.log("嘲笑我吧");
        }
    }
    //01 对象.属性
    var p1 = new Person();
    console.log(p1.des);
    //console.log(Person.prototype.des);
    p1.logDes();
    console.log(p1.age);
function Person(){
    }
    Person.prototype = {
        constructor:Person,
        des :"描述信息",
    }
    var p1 = new Person();
    var p2 = new Person();
    //设置
    //左值 --- 右值
    //如果是左值,那么在设置对象的属性的时候,不会去原型对象上面去找(查找自己是否有,如果有就是修改,没有就是添加)
    //如果是右值,那么在读取值得时候,先查找自己,如果找不到,再去原型身上找

    //  p1.hello(左值) = "hi"(右值);
    Person.prototype.hello = "hello";
    p1.hello = "hi";

    console.log(p1.hello);  //hi
    console.log(p2.hello);  //hello
function Person(){};
    Person.prototype.className = "逍遥派修仙技能班01";
    Person.prototype.showClassName = function(){console.log(this.className)};
    Person.prototype.car = {type:"火车",price:"$ 44444.44"};

    var p1 = new Person();
    var p2 = new Person();
    p1.showClassName();

    p1.className = "洗衣服小白";
    console.log(p1);
    console.log(p2);

    //如果原型对象的属性是引用类型的
    p1.car.type = "飞船";

    console.log(p1.car.type);   //飞船
    console.log(p2.car.type);   //飞船

    //补充
    p1.car = {type:"火箭"};
    console.log(p1.car.type);   //火箭
    console.log(p2.car.type);   //飞船

    p1.car = {};
    console.log(p1.car.type);   //undefined
    console.log(p2.car.type);   //飞船

指针

1.构造函数.prototype
2.对象.<proto>

    function Person(){}
    Person.prototype.des = "des";
    var p1 = new Person();

    console.log(Person.prototype == p1.__proto__);  //true

hasOwnProperty

1.检查对象中是否有指定的属性(实例属性 + 原型属性)
2.遍历对象
3.语法:“属性” in 对象

1.要求判断某个属性是否是原型属性,而且仅仅只是原型属性
2.该属性存在
3.该属性不是实例属性

Object.prototype.des = "des";
    Object.prototype.age = "des";
    var obj = {name:"zs",age:20};


    console.log("name" in obj);

    console.log(obj.hasOwnProperty("name"));

    console.log(obj.des);


    //in 和hasOwnProperty
    
    console.log("des" in obj);              //true
    console.log(obj.hasOwnProperty("des")); //false

    function isOnlyPrototypeProperty(propertyName,obj)
    {
        return (propertyName in obj) && !obj.hasOwnProperty(propertyName);
    }

    //验证
    console.log(isOnlyPrototypeProperty("name", obj));
    console.log(isOnlyPrototypeProperty("des", obj));
    console.log(isOnlyPrototypeProperty("age", obj));  //false

isPrototype

function Person(){};
    var demo = {};
    var demo1 = {};
    Person.prototype = demo;
    Person.prototype.constructor = Person;

    var p1 = new Person();

    //判断某个对象是否是指定对象的原型对象
    console.log(demo1.isPrototypeOf(p1));

思维导图 --> 如果图片不是很清晰的话 就下载下来保存到本地查看

**Js - 面向对象编程二**
上一篇 下一篇

猜你喜欢

热点阅读