[Javascript] The "this" keyword
The very first thing to understand when we're talking about this-keyword is really understand what's the purpose of the this-keyword is, or why we even have this-keyword in JavaScript.
What the this-keyword allows us to do, is it allows us to reuse functions with different contexts, or in other words it allows us to decide which objects should be focal when invoking a function or a methods. Imagine we had one function, and we had a bunch of objects that had similar properties, we want that function to work throughout all of our objects.
The first thing you need to ask yourself whenever you're trying to figure out what the this-keyword is, is this question. Where is this function invoked? We won't know what the this-keyword is in a function until that function is invoked.
There are four this keyword binding:
- Implicit Binding
- Explicit Binding
- New Binding
- Window Binding
- Implicit Binding
Implicit binding says that when you call a function and when the function is invoked, look to the left of the dot, and that is what the this-keyword is going to reference.
var me = {
name: "Wan",
age: 26,
sayName: function(){
console.log(this.name);
}
}
me.sayName();
var sayNameMixin = function(obj){
obj.sayName = function(){
console.log(this.name);
}
}
var you = {
name: "Zhenitan",
age: 27
}
sayNameMixin(me);
sayNameMixin(you);
me.sayName(); //wan
you.sayName(); //Zhentian
var Person = function(name, age){
return {
name: name,
age: age,
sayName: function(){
console.log(this.name);
},
mother: {
name: "Yun",
sayName: function(){
console.log(this.name);
}
}
}
}
var jim = Person('Jim', 42);
jim.sayNmae(); // Jim
jim.mother.sayNmae(); //Yun
you're going to find that whenever you get in these situation of trying to figure out what the this-keyword is, the very first thing you should do is look at when the function was invoked, and look if there's anything to the left of the dot, because if there is, that's what this-keyword is referencing.
- Explicit Binding
.call()
What if we were to take SayName out of this function? Instead of being a method on the object, now, it's just a function currently on the global scope. Now, what we want to do is we want to somehow call this function in the context of wan. What we can do is if we type the function name, every function has a .call property that allows us to do just that.
var sayName = function(){
console.log(this.name);
}
var wan = {
name: "Wan",
age: 27
};
sayName.call(wan);
let's go ahead and say if we wanted to pass a parameter, pass a few more arguments to SayName, what we can do is, let's say we had an array of languages.
var sayName = function(lang1, lang2, lang3){
console.log("My name is "+ this.name + ', and I know' + lang1 + ', '+ lang2 + ', '+ lang3);
}
var wan = {
name: "Wan",
age: 27
};
var languages = ['Javascript', 'Ruby', 'Python'];
sayName.call(wan, languages[0], languages[1], languages[2]);
What we can do here in .call, the very first argument you pass is the context, and every argument after that is going to be passed to the function, just as a normal argument.
.apply()
It would be nicer if we could just pass in languages, and some feature in the language of JavaScript would be able to parse these out to us.
var sayName = function(lang1, lang2, lang3){
console.log("My name is "+ this.name + ', and I know' + lang1 + ', '+ lang2 + ', '+ lang3);
}
var wan = {
name: "Wan",
age: 27
};
var languages = ['Javascript', 'Ruby', 'Python'];
sayName.apply(wan, languages);
.bind()
.bind is almost the exact same thing as .call, except there's one thing that's different. It returns a new function.
var sayName = function(lang1, lang2, lang3){
console.log("My name is "+ this.name + ', and I know' + lang1 + ', '+ lang2 + ', '+ lang3);
}
var wan = {
name: "Wan",
age: 27
};
var languages = ['Javascript', 'Ruby', 'Python'];
var newFn = sayName.bind(wan, languages[0],languages[1],languages[2]);
newFn();
To reacp, .call, apply and bind allow us to specifically state what this keyword will be within any given function. .call and .apply behave the same way, they will immediatelyh invoke that funciton, but with .call, you pass in arguments one by one, and with .apply, you pass them in as an array. .bind is the exact same thing as .call, but execpt for immediately invoking the function, it's going to return you a brand new function that you can invoke later.
- New Binding
var Animal = function(name, age){
// this = {};
this.name = name;
this.age = age;
};
var dog = new Animal('Zippy', 3);
When you use 'new' keyword, Javascript will auto create a 'this' keyword and assgin it as an object.
- Window Binding
var greeting = function(){
console.log(this.message);
}
greeting(); //undefined
window.message = "Hello";
greeting(); //"Hello"
In the console, we want to log out 'this.message', but we didn't use implict binding, so it shows undefined.
In javascript, if none of above three methods applyed, 'this' keyword will refer to the 'window' object, so if we assign
window.message = "Hello"
in greeting() will log out Hello.
To recap all our rules, we have implicit binding, which is you look to the left of the dot, at call time, explicit binding, which is telling a function what the context of the this keyword is going to be using call, apply, or bind.
The new binding is whenever you have a function invoked with the new keyword, the this keyword is bound to the new object being constructed. Then the Window binding where if none of these rules apply, then the this keyword is going to default to the Window object unless you're in strict mode. Then it's just going to be undefined.
[Javascript] The "this" keyword的更多相关文章
- javascript实例备忘
一,javascript动态显示: 如显示效果上图所示: 如图显示鼠标放在百度谷歌等字样上市动态显示其内容明细:代码如下:<head><title></title> ...
- Javascript的实例化与继承:请停止使用new关键字
本文同时也发表在我另一篇独立博客 <Javascript的实例化与继承:请停止使用new关键字>(管理员请注意!这两个都是我自己的原创博客!不要踢出首页!不是转载!已经误会三次了!) 标题 ...
- 我希望我知道的七个JavaScript技巧
如果你是一个JavaScript新手或仅仅最近才在你的开发工作中接触它,你可能感到沮丧.所有的语言都有自己的怪癖(quirks)——但从基于强类型的服务器端语言转移过来的开发人员可能会感到困惑.我就曾 ...
- Javascript + Dom知识点总结
Javascript + Dom知识点总结 1.用Javascript声明数组和字典的方式 // 数组声明 var arr = new Array(); arr["0"] = &q ...
- JavaScript Interview Questions: Event Delegation and This
David Posin helps you land that next programming position by understanding important JavaScript fund ...
- javascript fundamental concept
http://hzjavaeyer.group.iteye.com/group/wiki?category_id=283 上面这个url非常适合javascript初学者阅读,感谢原作者的分享 什么是 ...
- [转]JavaScript的实例化与继承:请停止使用new关键字
JavaScript中的new关键字可以实现实例化和继承的工作,但个人认为使用new关键字并非是最佳的实践,还可以有更友好一些的实现.本文将介绍使用new关键字有什么问题,然后介绍如何对与new相关联 ...
- Understand JavaScript’s “this” With Clarity, and Master It
The this keyword in JavaScript confuses new and seasoned JavaScript developers alike. This article a ...
- [ javascript ] getElementsByClassName与className和getAttribute!
对于javascript中的getElementsByClassName 在IE 6/7/8 不支持问题. 那么须要模拟出getElementsByClassName 须要採用className属性 ...
随机推荐
- 1.3 Content Provider
ContentProvider向我们提供了我们在应用程序之间共享数据的一种机制,分为系统的和自定义的,系统的也就是例如联系人,图片等数据. 使用方式:一个应用实现ContentProvider来提供内 ...
- iOS 直播(一)
由于业务需求,需要从腾讯直播sdk要迅速转移到自主开发(先让我默哀三分钟).不多说,直接开始唠嗑! 这个项目超级简单,简单到只能一个推流,一个拉流的功能.需求多的再另谈. 前期准备:推流用优酷开源的L ...
- Upstart 1.10 发布,系统初始化守护进程
Upstart 是一个用以替换 /sbin/init 守护进程的软件,基于事件机制开发.可用来处理启动过程中的任务和服务启动. Upstart 1.10 发布,改进记录: New bridges: u ...
- golang 远程传输文件
概述 之前有一篇介绍如何使用 golang 通过SSH协议来执行远程命令:golang 执行远程命令 同样,通过SSH协议也可以使用 golang 来远程传输文件. 除了 SSH 的库,为了传输文件, ...
- Session为null无法访问
我们在一般处理程序中需要访问Session为null 无法访问和操作 处理方案: 1.导入命名空间 System.Web.SessionState 2.实现IRequiresSessionState ...
- ASP.NET的一次奇遇:UserControl写成Control引发的w3wp进程崩溃
昨天在写代码中一不小心将UserControl写成了Control,将原来应该继承自System.Web.UI.UserControl的用户控件,比如下面的BlogStats: <%@ Cont ...
- kali Linux Web 渗透测试视频教程— 第六课 网络扫描-nmap与zmap
Kali Linux Web 渗透测试视频教程— 第六课 网络扫描-nmap与zmap 文/玄魂 目录 Kali Linux Web 渗透测试视频教程— 第六课 网络扫描-nmap与zmap. 1 N ...
- C++ Primer 快速入门
<C++ Primer 4th> 读书摘要 必须有一个命名为 main.操作系统通过 main 函数返回的值来确定程序是否成功执行完毕.返回 0 值表明程序程序成功执行完毕.任何其他非零的 ...
- AngularJS 源码分析3
本文接着上一篇讲 上一篇地址 回顾 上次说到了rootScope里的$watch方法中的解析监控表达式,即而引出了对parse的分析,今天我们接着这里继续挖代码. $watch续 先上一块$watch ...
- paip.java OutOfMemoryError 解决方法o33
paip.java OutOfMemoryError 解决方法o33 java.lang.OutOfMemoryError: Requested # java.lang.OutOfMemoryErro ...