new 运算符

new 运算符创建一个用户定义的对象类型的实例或具有构造函数的内置对象的实例。

语法:new constructor[([arguments])]

示例:

function Person(name, age) {
    this.name = name;
    this.age = age;
    this.sayName = function () {
      console.log(this.name);
    };
  }
  Person.prototype.sayHi = function () {
    console.log('I am ' + this.name);
  };

  var person1 = new Person('xiaoming', 18);
  console.log(person1.name); // xiaoming
  console.log(person1.age); // 18
  person1.sayName(); // xiaoming
  person1.sayHi(); // I am xiaoming

  console.log(person1 instanceof Person); //true

可以看到,使用new操作符后,返回了一个新对象,这个对象是new操作符后面的构造函数的实例。
该对象可以访问构造函数的属性和方法,也可以访问构造函数原型上的属性和方法。
在使用new运算符调用构造函数时的执行过程:
1.创建一个新对象
2.将构造函数中的this指向该对象
3.执行构造函数代码(给新对象添加属性和方法)
4.返回者着新对象
据此,我们初步实现模拟newnewTest方法:

  function myNew() {
    // 创建空对象
    var obj = {};
    // 第一个参数是构造函数
    var Constructor = [].shift.apply(arguments);
    // 将新对象的内部属性__proto__指向构造函数的原型,这样新对象就可以访问原型中的属性和方法
    obj.__proto__ = Constructor.prototype;
    // 不推荐直接更改__proto__,可使用Object.create()来创建对象
    // var obj = Object.create(Constructor.prototype);
    // 使用apply,将构造函数中的this指向新对象,这样新对象就可以访问构造函数中的属性和方法
    Constructor.apply(obj, arguments);
    return obj;
  }
  var person1 = myNew(Person, 'xiaoming', 18); // 测试通过

一般情况下,构造函数是没有返回值的。
如果返回值是基本类型:

  function Person(name, age) {
    this.name = name;
    this.age = age;
    this.sayName = function () {
      console.log(this.name);
    };
    return 'xiaoming';
  }
  Person.prototype.sayHi = function () {
    console.log('I am ' + this.name);
  };

  var person1 = new Person('xiaoming', 18);
  console.log(person1.name); // xiaoming
  console.log(person1.age); // 18
  person1.sayName(); // xiaoming
  person1.sayHi(); // I am xiaoming

如果返回值是一个对象:

  function Person(name, age) {
    this.name = name;
    this.age = age;
    this.sayName = function () {
      console.log(this.name);
    };
    return { name: 'xiaoming'};
  }
  Person.prototype.sayHi = function () {
    console.log('I am ' + this.name);
  };

  var person1 = new Person('xiaoming', 18);
  console.log(person1.name); // xiaoming
  console.log(person1.age); // undefined
  person1.sayName(); // Uncaught TypeError: person1.sayName is not a function
  person1.sayHi();

可以看出:
当返回基本类型时,new constructor[([arguments])] 相当于没有返回值时进行处理;
当返回一个对象时,只能访问构造函数返回的对象的属性和方法。

据此,我们对之前的myNew方法进行改进:

  function myNew() {
    // 创建空对象
    var obj = {};
    // 第一个参数是构造函数
    var Constructor = [].shift.apply(arguments);
    // 将新对象的内部属性__proto__指向构造函数的原型,这样新对象就可以访问原型中的属性和方法
    obj.__proto__ = Constructor.prototype;
    // 不推荐直接更改__proto__,可使用Object.create()来创建对象
    // var obj = Object.create(Constructor.prototype);
    // 使用apply,将构造函数中的this指向新对象,这样新对象就可以访问构造函数中的属性和方法
    var ret = Constructor.apply(obj, arguments);
    return typeof ret == 'object' ? ret : obj;
  }
  var person1 = myNew(Person, 'xiaoming', 18); // 测试通过
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值