理解new构造函数和apply以及call
今天在看设计模式的时候,遇到一些挺低级的东西,搞不懂,顾查阅资料整理记录一番。
先了解一下new构造函数的过程:
function func(){
console.log('do');
}
var foo = new func();
1、创建一个foo的空对象;
2、将func内部的this指向foo函数;(继承func函数内部的属性和方法)
3、foo._proto_ = func.prototye;(继承func的原型方法)
4、执行一遍foo,为其初始化;
5、返回一个foo对象;
(2018/04/17)补充:
1.创建一个foo空对象
2.foo._proto_ = func.prototype;
3.func.call(foo);
4.return foo;
二、call和apply的内部方法原理是一样的,只是使用方法不同。
先来一段官方定义:call和apply用于更改函数的执行上下文环境。
其实这样是很难理解的,到底什么意思呢?还是得上代码。
1)替换函数对象
function Cat() {
this.animal = 'cat';
console.log(this.animal);
}
function Dog() {
this.animal = 'dog';
}
Cat.call(Dog); //cat
内部执行可以分步骤进行:
1、Cat函数内部的this指向Dog函数;
2、执行Cat函数的函数上下文;
3、this.animal即为Dog.animal,因此Dog.animal赋值为‘cat’;
4、输出this.anmial即输出Dog.animal;
2)直接调用函数内部的方法
var func = {
txt : 'text',
showTxt : function() {
console.log(this.txt);
}
}
var foo = {
txt : 'document'
}
func.showTxt.call(foo); // document
步骤与例1差不多:
1、func的this指向foo;
2、执行func函数;
3、执行foo.showTxt函数;由于showTxt此时的调用者为foo,因此,showTxt内部的this指向foo,所以foo.txt为document;
此外,也有另一种请况:
function func() {
this.txt = 'text';
this.showTxt = function() {
console.log(this.txt);
}
}
function foo(){
this.txt = 'document';
}
func.showTxt.call(foo); // TypeError
这里会报错为TypeError,原因为并没有为foo对象进行初始化,只是执行了func的执行上下文。
如果是这样:
function func() {
this.txt = 'text';
this.showTxt = function() {
console.log(this.txt);
}
}
function foo(){
this.txt = 'document';
}
var m = new func();
var n = new foo();
m.showTxt.call(n); // document
外部函数的内部函数的调用必须经过初始化。
3)函数继承
function func(){
this.showName = function(){
console.log(1111);
}
}
function foo(){
func.call(this);
}
var son = new foo();
son.showName();//1111
理解了上面两个例子就容易理解了。
(2018/04/17)补充:
关于call和apply存在的意义:
var func1 ={
name : "jhon";
say : function() {
console.log(this.name)
}
}
obj = {name:"lili"};
func1.say.call(obj); // lili (注意:call和apply方法只能作用于Object对象上,Function上是不存在的)
理解new构造函数和apply以及call的更多相关文章
- 理解Angular中的$apply()以及$digest()
$apply()和$digest()在AngularJS中是两个核心概念,但是有时候它们又让人困惑.而为了了解AngularJS的工作方式,首先需要了解$apply()和$digest()是如何工作的 ...
- 深入理解js构造函数
JavaScript对象的创建方式 在JavaScript中,创建对象的方式包括两种:对象字面量和使用new表达式.对象字面量是一种灵活方便的书写方式,例如: ? 1 2 3 4 5 6 var o1 ...
- 深入理解Angular中的$Apply()以及$Digest()
$apply()和$digest()在AngularJS中是两个核心概念,但是有时候它们又让人困惑.而为了了解AngularJS的工作方式,首先需要了解$apply()和$digest()是如何工作的 ...
- 通俗理解angularjs中的$apply,$digest,$watch
<!DOCTYPE html> <html lang="zh-CN" ng-app="app"> <head> <me ...
- JS中面向对象的,对象理解、构造函数、原型、原型链
6.1 理解对象 6.1.1 对象属性类型 ECMS属性有两种类型:数据属性和访问器属性 1 数据属性 [[configurable]] 表示能否通过Delete 删除属性从而从新定义属性,能否修改属 ...
- 深入理解javascript构造函数和原型对象
---恢复内容开始--- 对象,是javascript中非常重要的一个梗,是否能透彻的理解它直接关系到你对整个javascript体系的基础理解,说白了,javascript就是一群对象在搅..(哔! ...
- (网页)理解Angular中的$apply()以及$digest()
转自CSDN: 工作有问题上CSDN上转转. $apply()和$digest()在AngularJS中是两个核心概念,但是有时候它们又让人困惑.而为了了解AngularJS的工作方式,首先需要了解$ ...
- (转) 理解Angular中的$apply()以及$digest()
原文地址:http://blog.csdn.net/dm_vincent/article/details/38705099 $apply()和$digest()在AngularJS中是两个核心概念,但 ...
- 深入理解Thread构造函数
上一篇快速认识线程 本文参考汪文君著:Java高并发编程详解. 1.线程的命名 在构造现成的时候可以为线程起一个名字.但是我们如果不给线程起名字,那线程会有一个怎样的命名呢? 这里我们看一下Threa ...
随机推荐
- Zabbix 3.0 基础介绍 [一]
zabbix 简介 Zabbix 是一个高度集成的网络监控解决方案,可以提供企业级的开源分布式监控解决方案,由一个国外的团队持续维护更新,软件可以自由下载使用,运作团队靠提供收费的技术支持赢利 zab ...
- WebVR认识
什么是WebVR WebVR是一种开放标准,可以在浏览器中体验VR,目标是让每个人都能轻松进入虚拟现实体验.
- P1629 邮递员送信
题目描述: 有一个邮递员要送东西,邮局在节点1.他总共要送N-1样东西,其目的地分别是2~N.由于这个城市的交通比较繁忙,因此所有的道路都是单行的,共有M条道路,通过每条道路需要一定的时间.这个邮递员 ...
- 实践作业2:黑盒测试实践——安装配置测试工具 Day 3
安装配置Katalon Studio工具 1.找下载Katalon链接,需要有效电子邮件才能激活Katalon账户,在我的Gmail里注册. 2.选择下载版本 3.下载完成后 ,转到计算机上的文件夹, ...
- Ubuntu 16.04 安装wine QQ
1.进入 http://www.ubuntukylin.com/application/show.php?lang=cn&id=279下载Wine QQ 2.解压压缩包 3.将文件夹中三个de ...
- java 之 命令模式(大话设计模式)
命令模式,笔者一直以为当我们开发的过程中基本上很难用到,直到维护阶段或者重构阶段,我们会发现有些撤销命令和追加命令比较频繁时,自然而然就用到命令模式. 先看下类图 大话设计模式-类图 简单说下类图,最 ...
- (一)—Linux安装与硬盘分区
相信很多人对linux充满了喜爱,尤其是技术人员,玩惯了windows更想尝试一下这个系统.关于它的优点多多,当然,你的好你的坏,用过才明白!下面我这个菜鸟也来玩装个玩玩. 我不会那么冲动,上来就把自 ...
- netty详解之io模型
提起IO模型首先想到的就是同步,异步,阻塞,非阻塞这几个概念.每个概念的含义,解释,概念间的区别这些都是好理解,这里深入*nix系统讲一下IO模型. 在*nix中将IO模型分为5类. Blocking ...
- Java-----关于线程池的使用
关于线程的相关概念不在此阐述,请百度或谷歌之 对于学习线程来说,我认为从代码开始学习比较好,前提是有一定的技术的积累,否则请关闭不用再看了~ 线程池四种实现方式. ①可缓存线程池,如果线程池长度超过处 ...
- Android安全专项-利用androguard分析微信
androguard Androguard经常使用API学习1 安装 做 Android 安全測试之前你应该知道的工具 (一) 分析 ./androlyze.py -s进入分析的交互界面 然后运行 a ...