【原】javascript笔记之this用法
javascript中的this学习起来相对复杂,最近花了点时间研究,总结起来大概这只有5种情况,相信只要熟悉这5种用法,基本是可以解决所有的this问题,文本不介绍this设计原理,只介绍用法,阅读本文,你需要了解javascript执行上下文环境,博主写这种文章的目的,主要还是给自己做下笔记,后续也会输出javascript的学习笔记。
全局代码中的this & 调用普通函数中的this & this作为对象的属性值
全局代码中的this ,永远是window。
//全局环境下,this永远是window。
console.info(this === window);// true //定义全局对象的属性
this.cat = '猫'; // global.cat = '猫'
console.info(cat); // 猫 //给一个无标示符变量赋值
dog = '狗';
console.info(this.dog); // '狗' //通过变量声明
var bird = '鸟';
console.info(this.bird); // '鸟'
调用普通函数中的this,永远是window。
function fn1() {
this.cat = '包子'
console.info(this);//Window {postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, frames: Window, …}
console.info(this.cat);//包子
}
fn1()
this作为对象的属性值,永远是window。
let obj = {
cat : '猫宝宝',
cat_father : this,
cat_self : this.cat
}
console.info(obj.cat_father);//Window {postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, frames: Window, …}
console.info(obj.cat_self);//undefined
其它注意:任何时候不能改变this的值。
//报错,任何时候不能改变this的值
this = '鸟'
构造函数中this
函数作为构造函数用,那么其中的this就代表它即将new出来的对象。
function Fn2() {
this.cat = '包子',
this.dog = '饺子'
console.info(this);//Fn2 {cat: "包子", dog: "饺子"}
}
let fn2 = new Fn2();
console.info(fn2.cat);//包子
console.info(fn2.dog);//饺子
原型链中this
在构造函数的prototype中,this代表函数即将new出来的对象。
function Fn3() {
this.cat = '包子'
}
Fn3.prototype.getItem = function(){
return this.cat;
}
let fn3 = new Fn3();
console.info(fn3.getItem());//包子
其实,不仅仅是构造函数的prototype,即便是在整个原型链中,this代表的也都是当前对象的值。
函数作为对象的一个属性被调用
函数作为对象的一个属性被调用,函数中的this指向调用它的对象,加深红色的这句话非常关键。
let obj = {
cat : '猫宝宝',
fn : function(){
console.info(this === obj);//true
console.info(this.cat);//猫宝宝
}
}
obj.fn()
又如小程序中,使用Page(Object) 函数用来注册一个页面,接受一个 Object 类型参数,那么this指向该Object
Page({
data: {
version: '1.0.1',
cat:'张老板他妹'
},
onLoad: function () {
console.info(this.data);//{version: "1.0.1", cat: "张老板他妹"}
}
})
在函数中this到底取何值,是在函数真正被调用执行的时候确定的,函数定义的时候确定不了。因为this的取值是执行上下文环境的一部分,每次调用函数,都会产生一个新的执行上下文环境,但最终函数中的this指向调用它的对象
let obj = {
cat: '大猫',
fn: function () {
console.info(this.cat)
}
};
//fn函数作为obj对象的一个属性被调用,在obj环境中执行,函数中的this指向该对象
obj.fn() // 大猫 var fn_new = obj.fn;
var cat = '小猫';//全局环境的cat //fn函数赋值给变量fn_new的时候并没有执行,此时this指向window,那么执行fn_new()时,this.cat对应取值为window.cat
fn_new() // 小猫
再来一个例子,对象的中嵌套子对象,子对象的属性值为函数,函数被子对象调用,那么函数中的this指向子对象,也就是函数中的this指向调用它的对象)
let obj = {
cat: '大猫',
obj_in: {
fn: function () {
console.info(this.cat) //undefined
}
}
}
//fn函数是被obj_in对象所调用,所以this指向的也obj_in对象
obj.obj_in.fn();
最后一个例子,对象的属性为函数,函数中嵌套函数,this放在嵌套函数中的情况
let obj = {
cat : '猫',
fn : function(){
function fn_in(){
console.info(this);//Window {postMessage: ƒ, blur: ƒ, focus: ƒ, close: ƒ, frames: Window, …}
console.info(this.cat);//undefined
}
//执行fn函数后,嵌套函数fn_in在fn环境中执行,回到文章中说的第一种情况,此时fn_in是普通函数,则它的this指向window
fn_in();
}
}
obj.fn()
函数用call或apply或bind调用
当一个函数被call和apply调用时,this的值就取传入的对象的值。
let obj1 = {
baobao : '猫'
}
let obj2 = {
baobao : '羊'
}
let obj3 = {
baobao : '鹅'
}
let fn3 = function(){
console.info(this.baobao);
}
fn3.apply(obj1);//猫
fn3.call(obj2);//羊
fn3.bind(obj3)();//鹅
同函数作为对象的一个属性被调用一样,函数fn4_in是在obj.fn4内部定义的,所以它仍然是一个普通的函数,this仍然指向window。
let obj3 = {
baobao : '猫'
}
let fn4 = function(){
function fn4_in(){
console.info(this.baobao);//undefined
}
fn4_in()
}
fn4.apply(obj3);
参考资料
http://www.ruanyifeng.com/blog/2018/06/javascript-this.html
http://www.cnblogs.com/TomXu/archive/2012/01/17/2310479.html
http://www.cnblogs.com/wangfupeng1988/p/3988422.html
【原】javascript笔记之this用法的更多相关文章
- 【原】javascript笔记之Array方法forEach&map&filter&some&every&reduce&reduceRight
做前端有多年了,看过不少技术文章,学了新的技术,但更新迭代快的大前端,庞大的知识库,很多学过就忘记了,特别在项目紧急的条件下,哪怕心中隐隐约约有学过一个方法,但会下意识的使用旧的方法去解决,多年前ES ...
- [Effective JavaScript 笔记]第3章:使用函数--个人总结
前言 这一章把平时会用到,但不会深究的知识点,分开细化地讲解了.里面很多内容在高3等基础内容里,也有很多讲到.但由于本身书籍的篇幅较大,很容易忽视对应的小知识点.这章里的许多小提示都很有帮助,特别是在 ...
- jQuery学习笔记之Ajax用法详解
这篇文章主要介绍了jQuery学习笔记之Ajax用法,结合实例形式较为详细的分析总结了jQuery中ajax的相关使用技巧,包括ajax请求.载入.处理.传递等,需要的朋友可以参考下 本文实例讲述了j ...
- javascript confirm()函数的用法
javascript confirm()函数的用法 confirm():确认消息对话框.用于允许用户做选择的动作.弹出的对话框中包含一确定按钮和一取消按钮. confirm(str) 参数说明: st ...
- [Effective JavaScript 笔记] 第4条:原始类型优于封闭对象
js有5种原始值类型:布尔值.数字.字符串.null和undefined. 用typeof检测一下: typeof true; //"boolean" typeof 2; //&q ...
- [Effective JavaScript 笔记] 第5条:避免对混合类型使用==运算符
“1.0e0”=={valueOf:function(){return true;}} 是值是多少? 这两个完全不同的值使用==运算符是相等的.为什么呢?请看<[Effective JavaSc ...
- [Effective JavaScript 笔记]第27条:使用闭包而不是字符串来封装代码
函数是一种将代码作为数据结构存储的便利方式,代码之后可以被执行.这使得富有表现力的高阶函数抽象如map和forEach成为可能.它也是js异步I/O方法的核心.与此同时,也可以将代码表示为字符串的形式 ...
- [Effective JavaScript 笔记]第28条:不要信赖函数对象的toString方法
js函数有一个非凡的特性,即将其源代码重现为字符串的能力. (function(x){ return x+1 }).toString();//"function (x){ return x+ ...
- javascript中的继承用法
本文实例汇总了javascript关于继承的用法,希望本文所述对大家的javascript程序设计有所帮助.分享给大家供大家参考.具体如下:代码如下: /** * 实现子类继承父类,但不会产生多余的属 ...
随机推荐
- lvs+keepalive实现主从效果,以及RS健康监测和tcp,udp实现非web的负载均衡
前面文章讲到了tcp和udp负载均衡,但是没有健康监测,这几天我优化了一下上次的操作.当然,我也是用的跨网段的通讯,因为线上业务主要是海外业务,所以做了iptables流量转发 IP: lvs-mas ...
- 对JavaScript事件机制的一点理解
JavaScript通过事件机制实现了异步操作,这种异步操作可以使CPU可以在IO任务的等待中被释放出来处理其他任务,等待IO结束再去处理这个任务.这个是一个基本的事件机制. 那么是不是说事件从监听到 ...
- SpringBoot整合Kafka和Storm
前言 本篇文章主要介绍的是SpringBoot整合kafka和storm以及在这过程遇到的一些问题和解决方案. kafka和storm的相关知识 如果你对kafka和storm熟悉的话,这一段可以直接 ...
- JAVA之单源最短路径(Single Source Shortest Path,SSSP问题)dijkstra算法求解
题目简介:给定一个带权有向图,再给定图中一个顶点(源点),求该点到其他所有点的最短距离,称为单源最短路径问题. 如下图,求点1到其他各点的最短距离 准备工作:以下为该题所需要用到的数据 int N; ...
- Flask入门之Virtualvenv的安装及使用(windows)
Virtualvenv 提供一个特定的Python虚拟环境(沙盒),以便于那些要求特定版本的模块的脚本能够顺利运行. 因为在Virtualvenv中,我们可以使用 pip install -r req ...
- ARCGIS 数据格式
1. 开篇 刚开始接触 GIS 时,老师说过这样一句话"做我们这一行的,数据就是命,没有数据,什么都干不了".现在我们需要做一个 webgis 的小项目,体会到了这句阐述的精髓.数 ...
- synchronized修饰方法和代码块的区别
先看一段代码 Class A { public synchronized methodA() {//对当前对象加锁 } public methodB() { synchronized(this){}/ ...
- Spring boot +Spring Security + Thymeleaf 认证失败返回错误信息
[Please make sure to select the branch corresponding to the version of Thymeleaf you are using] Stat ...
- Android 自定义控件实现刮刮卡效果 真的就只是刮刮卡么
转载请标明出处:http://blog.csdn.net/lmj623565791/article/details/40162163 , 本文出自:[张鸿洋的博客] 很久以前也过一个html5的刮刮卡 ...
- 手机端实现fullPage——全屏滚动效果
封装了一个小插件模拟fullPage的全屏滚动效果,比较简单. 特点: 1. 纯js实现,小巧轻便. 2. 兼容性好.苹果.安卓都没问题,暂时没遇到问题机型. 缺点: 1. 仅封装了基础功能,H ...