【JS】JS中对于this的理解
一、对this的产生原因分析和了解
第一:this
指的是函数运行时所在的环境(即调用的对象)。
第二:JavaScript 语言之所以有this
的设计,跟内存里面的数据结构有关系(内存存储详细理解参考原文)。
总结如下:
对于普通对象的保存:实际对象属性的值就是值;
对于函数的保存:实际函数属性的值是函数的地址;(而函数本身,可理解为:它不属于任何一个对象,相当于一个全局对象。所以,函数在不同场景下运行,this就是不同的场景了,不过都是执行时的环境)
同时,函数,可以作为一个参数(值)被调用,被传播。同时,在函数体内部,允许引用当前环境的其他变量(可以引用当前环境的其他变量。但当前环境是不确定的,所以会出现不同的值)
二、this绑定详解
this
实际上是在函数被调用时发生的绑定,它指向什么地方完全取决于函数在哪里被调用。
2.1 默认绑定(绑定在全局作用域)
即在调用函数时,函数不带任何修饰,也就是“光秃秃”的调用(即没有任何修饰的调用),就会应用默认绑定规则, 默认绑定指向全局作用域。
注意:在 javascript 中,如果使用了严格模式,则 this
不能绑定到全局对象。(不是很理解,不过先记录下)
2.2 隐式绑定
当函数在调用时,如果函数有所谓的“落脚点”,即有上下文对象(即调用时.
前面的对象)时,隐式绑定规则会把函数中的 this 绑定到这个上下文对象。
function say() {
console.log(this.name)
}
var name = "global"
var obj = {
name: "inside",
say: say
}
var alias = obj.say // 设置一个简写 (1)
alias() // 函数调用 输出"global" (2)
注意:隐式绑定时丢失上下文问题。
这个可以结合函数的存储理解为:obj.say
只是一个函数地址,不是函数本身。所以调用时,还是在当前全局环境下调用。
2.3 显式绑定:apply
,call
,bind
javascript中提供三种显式绑定方法:apply
,call
,bind
。
apply |
call |
bind |
---|---|---|
相同点 | apply 和call 的用法基本相似 |
apply 和call 的用法基本相似 |
不同点 | apply(obj,[arg1,arg2,arg3,...] 被调用函数的参数以数组的形式给出 |
call(obj,arg1,arg2,arg3,...) 被调用函数的参数依次给出 |
作用 | apply , call 的作用就是给函数绑定一个执行上下文,且是显式绑定的。但传入参数时会有所不同。 |
同左 |
注意:bind返回一个新函数,这个函数已经制定了执行上下文(这表示执行上下文在之后不可改变了),而返回这个新函数可以接受参数(即在绑定的执行上下文中,以参数为入参执行函数)。
2.4 new 绑定
new 绑定:指通过 new
操作符调用构造函数时发生的 this
绑定。
注意:在 javascript 中并没有其他语言那样的类的概念。构造函数也仅仅是普通的函数而已,只不过构造函数的函数名以大写字母开头,也只不过它可以通过 new
操作符调用而已。
实际上:new 和 bind
应该很类似。只是一个在创建时执行,一个在执行过程中执行。(不过还是很不同的,见下文区别)
2.5 bind 和 new 的区别
不过还是有区别的:bind只能被函数调用。而new 返回的是一个对象。即new 之后,函数的执行上下文就不可以被改变了,bind不行,显示绑定的三种形式都不行。所以new 绑定 的优先级最高。
2.6 四种绑定的优先级和区别:
默认绑定 < 隐式绑定 < 显式绑定 < new 绑定
注意:bind只能被函数调用。而new 返回的是一个对象。即new 之后,函数的执行上下文就不可以被改变了,bind不行,显示绑定的三种形式都不行。所以new 绑定 的优先级最高。
三、当 this 碰到 return :
注:主要参考:https://www.cnblogs.com/pssp/p/5216085.html
具体代码见原文,主要总结就是:
如果返回值是一个对象,那么 this 指向的就是那个返回的对象,如果返回值不是一个对象那么 this 还是指向函数的实例。(null是特例,虽然null是对象,但是返回时指向的还是函数的实例。)
即:函数返回对象时,那么this指向的是这个返回对象的运行环境;
函数返回不是对象时,那么this指向的就是这个函数本身。
四、参考
- JavaScript 的 this 原理 - 阮一峰的网络日志 http://www.ruanyifeng.com/blog/2018/06/javascript-this.html
- JavaScript中this绑定详解 - 想到什么写什么 - SegmentFault 思否 https://segmentfault.com/a/1190000007101339
- 彻底理解 js 中 this 的指向,不必硬背。 - 追梦子 - 博客园 https://www.cnblogs.com/pssp/p/5216085.html
注:另一篇比较详细的说明,和上面几篇的模式不同,不过讲解的也很清楚
【JS】JS中对于this的理解的更多相关文章
- js for (i=0;i<a.length;a[i++]=0) 中等于0怎么理解?
js的问题for (i=0;i<a.length;a[i++]=0) 中等于0怎么理解? 很奇怪的一个for循环 竟然是将原来数组的数据全改为0
- 对JS中事件委托的理解
什么是事件委托: 事件委托——给父元素绑定事件,用来监听子元素的冒泡事件,并找到是哪个子元素的事件.(不理解冒泡的可以去百度下) 定义:利用事件冒泡处理动态元素事件绑定的方法,专业术语叫事件委托. 使 ...
- js文件中函数前加分号和感叹号是什么意思?
本文转自:http://blog.csdn.net/h_o_w_e/article/details/51388500 !function(){}(); !有什么用? 从语法上来开,JavaScri ...
- Handlebars.js循环中索引(@index)使用技巧(访问父级索引)
使用Handlebars.js过程中,难免会使用循环,比如构造数据表格.而使用循环,又经常会用到索引,也就是获取当前循环到第几次了,一般会以这个为序号显示在页面上. Handlebars.js中获取循 ...
- JS 正则表达式中的特殊字符
正则表达式中的特殊字符 字符 含意 \ 做为转意,即通常在"\"后面的字符不按原来意义解释,如/b/匹配字符"b",当b前面加了反斜杆后/\b/,转意为匹配一个 ...
- js jquery中 的数据类型
任何一门语言, buguan 是动态的, 还是像C语言的, 都有严格的 类型 "概念的", 这个是由于 编译器和解释器要求的, 需要的. 所以在是使用像 js, jquey ,ph ...
- js代码中的闭包
作为一个后台开发人员了解前端非常重要,尤其是深处学校实验室做项目时前端把写好的代码直接给你,然后你在修改的时候.我经常做的就是修改前端的代码的HTML和后台交互的部分以及js的ajax部分,之后修改之 ...
- Web3.js API 中文文档
Web3.js API 中文文档 http://web3.tryblockchain.org/Web3.js-api-refrence.html web3对象提供了所有方法. 示例: //初始化过程 ...
- 编写高质量JS代码中
前段时间看了几道关于前端javascript的面试题目,方觉函数调用模式等基础的重要性.于是,下定决心,好好补补基础,即便不能深入语言的内部设计模式,也要对基本面向对象概念有比较深入的理解. 继续上一 ...
- 全面解析JavaScript的Backbone.js框架中的Router路由
这篇文章主要介绍了Backbone.js框架中的Router路由功能,Router在Backbone中相当于一个MVC框架中的Controller控制器功能,需要的朋友可以参考下. Backbone ...
随机推荐
- VS2012安装git
新安装了vs2012,尝试使用Git,安装过程比较简单,记录下来以备以后查阅. 1. 下载.安装Git 我的系统是Windows 7,需要安装Git for Windows. 下载地址: http ...
- java 重载和多态的区别
虚拟函数表是在编译期就建立了,各个虚拟函数这时被组织成了一个虚拟函数的入口地址的数组.而对象的隐藏成员--虚拟函数表指针是在运行期--也就是构造函数被调用时进行初始化的,这是实现多态的关键. http ...
- C#代码覆盖率 -vsinstr和OpenCover
最近接触的项目涉及到C#开发的应用,测试过程中我们需要去分析C#的代码覆盖率,问了一些人,在网上也搜了一些,零碎的找到很多资料,但是都不是很完整,实际使用的过程中还是走了不少弯路.到现在为止,有两种可 ...
- 关于audio标签播放跨域的问题
遇到过的错误: DOMException: The play() request was interrupted by a new load request. DOMException: Failed ...
- laravel数据库操作sql语句用Eloquent ORM来构造
现在有查询语句: SELECT users.sNmame, users.iCreateTime, users_ext.iAge, users_ext.sSex FROM users LEFT JOIN ...
- unity, 在surface shader中访问顶点色
//ref: Custom data computed per-vertex: http://docs.unity3d.com/Manual/SL-SurfaceShaderExamples.html ...
- Wpf 抽屉效果
在android开发中有抽屉效果,就是在页面的边上有一个按钮,可以通过点击或者拖拽这个按钮,让页面显示.Wpf也可以实现相同的效果. 主要是通过一个DoubleAnimation和RectAnimat ...
- JS检查浏览器类型和版本号
先取得Navigator对象的userAgent属性的小写信息,之后依据正則表達式推断赋值. var Sys = {}; var ua = navigator.userAgent.toLowerCas ...
- 修复Win10下Synaptics触摸板双指触击无法打开右键菜单的问题
从Win8.1开始,Synaptics触摸板驱动的键值就不能正确设置,使得双指触击失效,无法打开右键菜单. 解决方法1.打开注册表:2.搜索“2FingerTapAction”,或直接定位到以下两个路 ...
- ubuntu 安装 qt等软件
1 ubuntu安装qt4 sudo apt-get install qt4-dev-tools qt4-designer qt4-doc qt4-qtconfigqt4-demos qt4-qmak ...
- JavaScript 的 this 原理 - 阮一峰的网络日志 http://www.ruanyifeng.com/blog/2018/06/javascript-this.html
- JavaScript中this绑定详解 - 想到什么写什么 - SegmentFault 思否 https://segmentfault.com/a/1190000007101339
- 彻底理解 js 中 this 的指向,不必硬背。 - 追梦子 - 博客园 https://www.cnblogs.com/pssp/p/5216085.html
注:另一篇比较详细的说明,和上面几篇的模式不同,不过讲解的也很清楚
js的问题for (i=0;i<a.length;a[i++]=0) 中等于0怎么理解? 很奇怪的一个for循环 竟然是将原来数组的数据全改为0
什么是事件委托: 事件委托——给父元素绑定事件,用来监听子元素的冒泡事件,并找到是哪个子元素的事件.(不理解冒泡的可以去百度下) 定义:利用事件冒泡处理动态元素事件绑定的方法,专业术语叫事件委托. 使 ...
本文转自:http://blog.csdn.net/h_o_w_e/article/details/51388500 !function(){}(); !有什么用? 从语法上来开,JavaScri ...
使用Handlebars.js过程中,难免会使用循环,比如构造数据表格.而使用循环,又经常会用到索引,也就是获取当前循环到第几次了,一般会以这个为序号显示在页面上. Handlebars.js中获取循 ...
正则表达式中的特殊字符 字符 含意 \ 做为转意,即通常在"\"后面的字符不按原来意义解释,如/b/匹配字符"b",当b前面加了反斜杆后/\b/,转意为匹配一个 ...
任何一门语言, buguan 是动态的, 还是像C语言的, 都有严格的 类型 "概念的", 这个是由于 编译器和解释器要求的, 需要的. 所以在是使用像 js, jquey ,ph ...
作为一个后台开发人员了解前端非常重要,尤其是深处学校实验室做项目时前端把写好的代码直接给你,然后你在修改的时候.我经常做的就是修改前端的代码的HTML和后台交互的部分以及js的ajax部分,之后修改之 ...
Web3.js API 中文文档 http://web3.tryblockchain.org/Web3.js-api-refrence.html web3对象提供了所有方法. 示例: //初始化过程 ...
前段时间看了几道关于前端javascript的面试题目,方觉函数调用模式等基础的重要性.于是,下定决心,好好补补基础,即便不能深入语言的内部设计模式,也要对基本面向对象概念有比较深入的理解. 继续上一 ...
这篇文章主要介绍了Backbone.js框架中的Router路由功能,Router在Backbone中相当于一个MVC框架中的Controller控制器功能,需要的朋友可以参考下. Backbone ...
新安装了vs2012,尝试使用Git,安装过程比较简单,记录下来以备以后查阅. 1. 下载.安装Git 我的系统是Windows 7,需要安装Git for Windows. 下载地址: http ...
虚拟函数表是在编译期就建立了,各个虚拟函数这时被组织成了一个虚拟函数的入口地址的数组.而对象的隐藏成员--虚拟函数表指针是在运行期--也就是构造函数被调用时进行初始化的,这是实现多态的关键. http ...
最近接触的项目涉及到C#开发的应用,测试过程中我们需要去分析C#的代码覆盖率,问了一些人,在网上也搜了一些,零碎的找到很多资料,但是都不是很完整,实际使用的过程中还是走了不少弯路.到现在为止,有两种可 ...
遇到过的错误: DOMException: The play() request was interrupted by a new load request. DOMException: Failed ...
现在有查询语句: SELECT users.sNmame, users.iCreateTime, users_ext.iAge, users_ext.sSex FROM users LEFT JOIN ...
//ref: Custom data computed per-vertex: http://docs.unity3d.com/Manual/SL-SurfaceShaderExamples.html ...
在android开发中有抽屉效果,就是在页面的边上有一个按钮,可以通过点击或者拖拽这个按钮,让页面显示.Wpf也可以实现相同的效果. 主要是通过一个DoubleAnimation和RectAnimat ...
先取得Navigator对象的userAgent属性的小写信息,之后依据正則表達式推断赋值. var Sys = {}; var ua = navigator.userAgent.toLowerCas ...
从Win8.1开始,Synaptics触摸板驱动的键值就不能正确设置,使得双指触击失效,无法打开右键菜单. 解决方法1.打开注册表:2.搜索“2FingerTapAction”,或直接定位到以下两个路 ...
1 ubuntu安装qt4 sudo apt-get install qt4-dev-tools qt4-designer qt4-doc qt4-qtconfigqt4-demos qt4-qmak ...