• 关于 this 和 prototype 的理解


    1:this 的理解比较好的书是 《Javascript语言精粹》

      平时我们全局写 var a = 1, 其实就是 window.a = 1;

      var f = function(){}, 其实就是 window.f = function(){}

      当执行 f(), 相当于执行 window.f(), 那么f 里的 this 是调用它的对象, 即window

      var obj = {f: function(){} }, 当执行 obj.f(); 那么调用 f 的是 obj对象, 则 f 里的 this 指向 obj

      看下面的代码,当执行 obj.f() 时, f 里面的 this 指向obj, 但是 func 里面的 this 不是指向obj, 这是 语言设计上的一个错误;

      从另一个层面上说,在 obj.f 函数里面是 没有对象调用func,这个时候我们默认定义它的 this 是 window

    var obj = {
        a: 1,
        f: function(){
            var func = function(){
                console.log(this.a);
            }
            func();
        }
    }

      总结: 

      this 的指向就是谁调用这个函数, this 就是指向谁。

      比如 obj.f(), this 指向 obj;  obj.obj2.obj3.f(), this 指向 obj.obj2.obj3。

      当找不出调用这个函数的对象时, this 指向 window.

    2: prototype 的理解

      

    1. 理解原型对象

      下面这段话来自 《Javascript 高级程序设计 3版》

      无论什么时候,只要创建了一个新函数,就会根据一组特定的规则为该函数创建一个prototype属性,这个属性指向函数的原型对象。在默认情况下,所有原型对象都会自动获得一个constructor(构造函数)属性,这个属性包含一个指向prototype 属性所在函数的指针。就拿前面的例子来说,Person.prototype. constructor 指向Person。而通过这个构造函数,我们还可继续为原型对象添加其他属性和方法。

      创建了自定义的构造函数之后,其原型对象默认只会取得constructor 属性;至于其他方法,则都是从Object 继承而来的。当调用构造函数创建一个新实例后,该实例的内部将包含一个指针(内部属性),指向构造函数的原型对象。ECMA-262 第5 版中管这个指针叫[[Prototype]]。虽然在脚本中没有标准的方式访问[[Prototype]],但Firefox、Safari 和Chrome 在每个对象上都支持一个属性__proto__;而在其他实现中,这个属性对脚本则是完全不可见的。不过,要明确的真正重要的一点就是,这个连接存在于实例与构造函数的原型对象之间,而不是存在于实例与构造函数之间。

      

    var F = function(){}
    F.prototype = {
        a: 1,
        exec: function(){ console.log(1);}
    }
    
    var ins = new F;
    ins.exec();
    

      

      定义一个函数以后,F的属性F.prototype 指向了一个对象, 这个对象叫做原型对象。 这样理解 F = {prototype: 原型对象}

      当实例化的时候,ins 里面的 __proto__ 指向了也是指向了原型对象。ins = {__proto__: 原型对象}

      

      所以下面的代码为什么会输出不了? 

      

    var F = function(){}
    var ins = new F;
    F.prototype = {
        a: 1,
        exec: function(){ console.log(1);}
    }
    ins.exec(); // 能输出1吗?

      相当于:

      var _obj = {}; // _obj  只是用来说明问题对象

      var proto = _obj; // 定义了函数以后,proto 即 F.prototype 对象, 指向_obj

      var ins = _obj; // 相当于 ins 初始化以后,也指向_obj

      proto = otherObj; // proto 指向其它的对象

      ins.exec(); // exec 为 otherObj 里面的方法,那么执行 ins.exec 报错。

    《Javascript 语言精粹》里面给出了 new 的时候, 到底做了什么事

      

    typeof Function;     // 'function'
    typeof String;         // 'function'
    typeof Number;     // 'function'
    
    Function.prototype.method = function(name, func){
      this.prototype[name] = func;
      return this;
    }
    
    String.method('trim', function(){});
    //相当于:
    String.prototype.trim = function(){};
    
    Object.beget = function(o){
      var F = function(){};
      F.prototype = o;
      return new F();
    }
    
    Function.method('new', function(){
      var that = Object.beget(this.prototype);
      var other = this.apply(that, arguments);
      return (typeof other === 'object' && other) || that;
    });
    
    var F = function(){};
    var f = new F(); // 相当于 var f = F.new();  里面的上面的 this 相当于 F
  • 相关阅读:
    使用urllib
    spring常用的45个注解
    音痴
    android与JS函数传参遗留问题
    方舟编译器源码过一遍流程
    什么是语义学,解释器
    synchronized,ReentrantLock解决锁冲突,脏读的问题
    【Unity3d】ScrollRect自动定位到某点
    计算点到直线的距离】 C#实现
    理财-房月供占工资多少比较合适?
  • 原文地址:https://www.cnblogs.com/zhengming2016/p/5521151.html
Copyright © 2020-2023  润新知