this是什么

this就是函数内部的关键字

看下面例子理解js中的this

    // 例子1
function fnOne () {
console.log(this)
}
'use strict'
function fnOne () {
console.log(this)
}
// 例子2
let a = {
txt: 'hello world',
fn: function() {
console.log(this.txt)
}
}
a.fn()
window.a.fn()
// 例子3
let b = {
txt: 'hello',
obj: {
txt: 'world',
fn: function(){
console.log(this.txt)
console.log(this)
}
}
}
let c = {
txt: 'hello',
obj: {
// txt: 'world',
fn: function(){
console.log(this.txt)
}
}
}
b.obj.fn()
c.obj.fn()
let d = b.obj.fn
d()
    // 例子4
function Fn () {
this.txt = 'hello world'
}
let e = new Fn()
e.txt
// 例子5
function Fn () {
this.txt = 'hello world'
return {txt:'hello'}
}
function Fn () {
this.txt = 'hello world'
return [1]
}
function Fn () {
this.txt = 'hello world'
return 1
}
function Fn () {
this.txt = 'hello world'
return null
}
function Fn () {
this.txt = 'hello world'
return undefined
}
let e = new Fn()
e.txt
// 带有{}或者[]返回值的方法实例化时this指向被改变
    // 例子6
// 箭头函数与包裹它的代码共享相同的this对象
// 如果箭头函数在其他函数的内部
// 它也将共享该函数的arguments变量
let bob = {
_name: "Bob",
_friends: [],
printFriends: () => {
console.log(this._name)
console.log(this)
}
}
let bob = {
_name: "Bob",
_friends: [],
printFriends() {
console.log(this._name)
console.log(this)
}
} let bob = {
_name: "Bob",
_friends: [1],
printFriends() {
this._friends.forEach((item) => {
console.log(this._name)
})
}
}
// arguments 对象
function square() {
let example = () => {
let numbers = [];
for (let number of arguments) {
numbers.push(number * number);
} return numbers;
}; return example();
} square(2, 4, 7.5, 8, 11.5, 21); // returns: [4, 16, 56.25, 64, 132.25, 441]

this的指向

this永远指向的是最后调用它的对象(箭头函数除外)

this的应用

如何改变函数的this指向 apply call bind

三者的区别apply和call改变函数this而且是立即执行。bind(es5新加方法注意兼容性)是复制函数,不会立即执行。根据各自执行时机的不同来选择采用哪种方案。

function Product(name, price) {
this.name = name
this.price = price
}
function Food(name, price) {
Product.call(this, name, price)
// Product.apply(this, arguments)
this.category = 'food'
}
console.log(new Food('cheese', 5).name)

bind用法和可以解决的问题

// 解决,从对象中拿出方法定义给新变量,但是希望方法的this值保持不变这时可以用bind来绑定this
this.x = 9;
var module = {
x: 81,
getX: function() { return this.x; }
};
module.getX(); // 返回 81
var retrieveX = module.getX;
retrieveX(); // 返回 9, 在这种情况下,"this"指向全局作用域
// 创建一个新函数,将"this"绑定到module对象
// 新手可能会被全局的x变量和module里的属性x所迷惑
var boundGetX = retrieveX.bind(module);
boundGetX(); // 返回 81 // bind配合setTimeout()
function LateBloomer() {
this.petalCount = Math.ceil(Math.random() * 12) + 1;
}
LateBloomer.prototype.bloom = function() {
window.setTimeout(this.declare.bind(this), 1000);
}
LateBloomer.prototype.declare = function() {
console.log('I am a beautiful flower with ' +
this.petalCount + ' petals!');
}
var flower = new LateBloomer();
flower.bloom(); // 一秒钟后, 调用'declare'方法

箭头函数的this使用注意事项

1、函数体内的this对象,就是定义时所在的对象,而不是使用时所在的对象。
2、不可以当作构造函数,也就是说,不可以使用new命令,否则会抛出一个错误。
3、不可以使用arguments对象,该对象在函数体内不存在。如果要用,可以用 rest 参数代替。
4、不可以使用yield命令,因此箭头函数不能用作 Generator 函数。
5、不能使用apply/call/bind

// 箭头函数可以让setTimeout里面的this,绑定定义时所在的作用域,而不是指向运行时所在的作用域。下面是另一个例子。
function Timer() {
this.s1 = 0;
this.s2 = 0;
// 箭头函数
setInterval(() => this.s1++, 1000);
// 普通函数
setInterval(function () {
this.s2++;
}, 1000);
} var timer = new Timer(); setTimeout(() => console.log('s1: ', timer.s1), 3100);
setTimeout(() => console.log('s2: ', timer.s2), 3100);
// s1: 3
// s2: 0
// 箭头函数可以让this指向固定化,这种特性很有利于封装回调函数。下面是一个例子,DOM 事件的回调函数封装在一个对象里面。
var handler = {
id: '123456', init: function() {
document.addEventListener('click',
event => this.doSomething(event.type), false);
}, doSomething: function(type) {
console.log('Handling ' + type + ' for ' + this.id);
}
};

如何理解js中的this和实际应用中需要避开哪些坑的更多相关文章

  1. 怎么理解js中的事件委托

    怎么理解js中的事件委托 时间 2015-01-15 00:59:59  SegmentFault 原文  http://segmentfault.com/blog/sunchengli/119000 ...

  2. 如何更好的理解js中的this,分享2段有意思的代码

    关于js中this的浅析,大家可以点击[彻底理解js中this的指向,不必硬背]这篇博客了解. 今天遇到2段比较有意思的代码. ----------------第一段----------------- ...

  3. 【学习笔记】六:面向对象的程序设计——理解JS中的对象属性、创建对象、JS中的继承

    ES中没有类的概念,这也使其对象和其他语言中的对象有所不同,ES中定义对象为:“无序属性的集合,其属性包含基本值.对象或者函数”.现在常用的创建单个对象的方法为对象字面量形式.在常见多个对象时,使用工 ...

  4. 图文结合深入理解JS中的this值

    文章目录 Js 中奇妙的this值 1. 初探this 2. this指向总结 2.1 普通函数调用 2.2 对象的方法调用 2.3 构造函数调用 2.4 利用call,apply,bind方法调用函 ...

  5. 详细理解JS中的继承

    正式说继承之前,有两个相关小点: JS只支持实现继承,即继承实际的方法,不支持接口继承(即继承方法的签名,但JS中函数没签名) 所有对象都继承了Object.prototype上的属性和方法. 说继承 ...

  6. 图文结合深入理解 JS 中的 this 值

    图文结合深入理解 JS 中的 this 值 在 JS 中最常见的莫过于函数了,在函数(方法)中 this 的出现频率特别高,那么 this 到底是什么呢,今天就和大家一起学习总结一下 JS 中的 th ...

  7. 深度理解js中var let const 区别

    首先要理解js中作用域的概念 作用域:指的是一个变量的作用范围 1.全局作用域 直接写在script中的js代码,在js中,万物皆对象,都在全局作用域,全局作用域在页面打开时创建,在全局作用域中有一个 ...

  8. 深入理解JS中的对象(二):new 的工作原理

    目录 序言 不同返回值的构造函数 深入 new 调用函数原理 总结 参考 1.序言 在 深入理解JS中的对象(一):原型.原型链和构造函数 中,我们分析了JS中是否一切皆对象以及对象的原型.原型链和构 ...

  9. 深入理解JS中的对象(三):class 的工作原理

    目录 序言 class 是一个特殊的函数 class 的工作原理 class 继承的原型链关系 参考 1.序言 ECMAScript 2015(ES6) 中引入的 JavaScript 类实质上是 J ...

随机推荐

  1. eclipse web 项目配置 运行

  2. 邪恶的csrf

    关于csrf是啥我就不多说了 进入正文 场景模拟 场景一 在一个bbs社区里,用户在发言的时候会发出一个这样的GET请求: #!html GET /talk.php?msg=hello HTTP/1. ...

  3. 郑宇以城市计算研究膺选 MIT 科技创新35俊杰 (TR35)

    MIT 科技创新35俊杰 (TR35)"> 编者按:<MIT Technology Review>于8月22日发布了令人瞩目的2013年全球杰出青年创新者(MIT TR35 ...

  4. WEB-文件包含漏洞详解

    title date tags layout 文件包含漏洞(File Include) 2018-10-12 post 产生原因: 由于在编写代码时避免麻烦就需要把公用的一段代码写到一个单独的文件里面 ...

  5. Linux_centos安装后无法进入图形界面

    问题 直接默认进入字符界面 root之后init 5也没用 解决方法 出现问题的原因在于安装时选择了最小安装,如图所示

  6. Jeninks远程部署war包

    主体上看别人的脚本,然后和开发协商,做出符合自己的生产脚本................................ 脚本一: #!/bin/bash DATE=`date +%F-%H-%M` ...

  7. servlet简单概括总结

    最近在看java web的相关内容,不管是整体还是细节,要学习的知识有很多,所以有一个好的学习体系非常重要.在阅读学习一些博客和教程中关于servlet的内容后,现将知识体系和自己的总结体会进行梳理, ...

  8. Python练习 ——名片管理系统(增添,删除,查找,修改)

    需要注意的一个地方是,如果你用的版本是3.6的,那么下面的用到的所有从外界接收信息所用到的input()用input()就行了,如果是2.7版本,那么如果接收的是字符串要用raw_input()(将接 ...

  9. 上传第三方jar包到nexus

    1.创建一个新的repository存放第三方jar包(3rd_party) 2.执行以下命令进行上传:切记需要上传的本地jar包路径不能在本地仓库下,可以随便放一个位置.(以下标红的,请根据自己情况 ...

  10. 如何用js判断一个对象是不是Array

    .如何用js判断一个对象是不是Array 1.Array.isArray(obj) 调用数组的isArray方法 2.obj instanceof Array 判断对象是否是Array的实例 3.Ob ...