一个对于js this关键字的问题


Posted in Javascript onJanuary 09, 2007

所以拿出来与大家共勉:
先运行以下的js代码
<script>
foo = {
 'bar': function () {
 alert(this);
 },
 'toString': function () {
 return 'foo';
 }
};
foo.bar();//返回的是"foo"
(foo.bar)();//返回的是"[object Window]"
(foo.bar || null)();//返回的是"[object Window]"
bar = foo.bar; bar();//返回的是"[object Window]"
</script>

我对这里的代码的解释:

foo.bar(); //打印foo
//1. alert隐式调用toString方法,转型成字符串,在foo里重写了toString方法,因此为foo

(foo.bar)();//打印foo
//2. 这里的执行同上

(foo.bar || null)();
/*
3. 这里在IE6.0,Mozilla Firefox1.5.0.7和Opera9.0里有不同的效果,IE和Opera都是object,Mozilla的为foo
暂且不谈这几个的JS对||的解释方法,这与bar方法中的this还有和||运算符是有关的。经过||之后
这里的this已经不再为window了,this关键字的作用,如果按照C++的理解,应该为动态联编,而非静态联编,我们平常的例子中
<script>
(function (){
this.div = document.createElement("div");div.innerHTML="never-online";
document.body.appendChild(div);
 this.div.onclick = function(){
 alert(this.tagName);//这里的this就是div而非匿名函数中的this
 }
})()
</script>
也就是说,这里this的作用域不再是foo对象,而是一个全局的作用域。因此alert(this)相当于alert(window);
所以为object

BTW:有可能是||运算符是要把两个表达式的执行转换为全局范围的比较,所以在IE和Opera中,这里(foo.bar || null)返回的是一个全局引用,即:
 'bar': function () {
 alert(this);//这里的this已经为全局this,全局的this,即为window
 },
详细的,我将在篇末加入一段代码,以示说明
*/

bar = foo.bar; bar();//返回的是"[object Window]"
/*4. 
这里在IE6.0,Mozilla Firefox1.5.0.7和Opera9.0里都为相同的object,如果理解上面的执行,理解这句显然会比较简单
理由同上,这里把foo.bar的引用给到一个全局变量bar,而全局变量都隶属于window的引用,看下面代码:
var a = 'never-online';
alert(this.a); //never-online
alert(window.a); //never-online
如果你尝试着把bar = foo.bar; bar();改成以下代码,或许就可以明白了
foo.alert = foo.bar; foo.alert ();
这里的foo.alert依然为foo对象的引用,因此foo对象里的this,在这里依然有效,并没有成为window object
因为很明显的bar属性window,因此引用foo.bar里虽然有this,但是this引用为window
*/

再看看我们把这个例子改成这样:
<script>
foo = {
 'bar': function () {
 var oSelf = this;
 alert(this.toString);
 if (oSelf==window) {
 oSelf = foo;
 }
 alert(oSelf);
 },
 'toString': function () {
 return 'foo';
 }
};

window.toString = function () {
 alert("引用全局this --- window");
}

foo.bar();
(foo.bar)();
(foo.bar || null)();
bar = foo.bar; bar();
</script>

这样应该明白原因了。

从这个例中(foo.bar || null)(); 可以看出Mozilla的解释器会更“标准”一些,而Opera和IE的解释方法则与Mozilla的不一样。||运算符的作用,出现了不同的效果。同我上面所说的, 有可能是||运算符是要把两个表达式的执行转换为全局范围的比较,所以在IE和Opera中,这里(foo.bar || null)返回的是一个全局引用 

Javascript 相关文章推荐
漂亮的widgets,支持换肤和后期开发新皮肤
Apr 23 Javascript
滚动图片效果 jquery实现回旋滚动效果
Jan 08 Javascript
Javascript基础教程之JavaScript语法
Jan 18 Javascript
JS实现判断碰撞的方法
Feb 11 Javascript
详解vue-router 路由元信息
Sep 13 Javascript
Node.js使用Koa搭建 基础项目
Jan 08 Javascript
Rollup处理并打包JS文件项目实例代码
May 31 Javascript
对angular4子路由&amp;辅助路由详解
Oct 09 Javascript
浅谈vue3中effect与computed的亲密关系
Oct 10 Javascript
24行JavaScript代码实现Redux的方法实例
Nov 17 Javascript
使用vue打包进行云服务器上传的问题
Mar 02 Javascript
OpenLayers3实现地图显示功能
Sep 25 Javascript
JS控件autocomplete 0.11演示及下载 1月5日已更新
Jan 09 #Javascript
根据分辩率调用不同的CSS.
Jan 08 #Javascript
如何用javascript判断录入的日期是否合法
Jan 08 #Javascript
[IE&amp;FireFox兼容]JS对select操作
Jan 07 #Javascript
javascript中的对象和数组的应用技巧
Jan 07 #Javascript
JavaScript For Beginners(转载)
Jan 05 #Javascript
JavaScript的目的分析
Jan 05 #Javascript
You might like
用PHP+MySql编写聊天室
2006/10/09 PHP
PHP 存取 MySQL 数据库的一个例子
2006/10/09 PHP
PHP读取数据库并按照中文名称进行排序实现代码
2013/01/29 PHP
PHP数据类型之布尔型的介绍
2013/04/28 PHP
PHP系统命令函数使用分析
2013/07/05 PHP
PHP获取浏览器信息类和客户端地理位置的2个方法
2014/04/24 PHP
php简单图像创建入门实例
2015/06/10 PHP
PHP的mysqli_ssl_set()函数讲解
2019/01/23 PHP
使用JavaScript动态设置样式实现代码(2)
2013/01/25 Javascript
判断客户浏览器是否支持cookie的示例代码
2013/12/23 Javascript
将json对象转换为字符串的方法
2014/02/20 Javascript
javascript事件冒泡详解和捕获、阻止方法
2014/04/12 Javascript
jquery+css3打造一款ajax分页插件(自写)
2014/06/18 Javascript
浅谈js对象属性 通过点(.) 和方括号([]) 的不同之处
2016/10/29 Javascript
基于node.js制作简单爬虫教程
2017/06/29 Javascript
基于vue手写tree插件的那点事儿
2019/08/20 Javascript
微信小程序实现定位及到指定位置导航的示例代码
2019/08/20 Javascript
Python正则表达式介绍
2012/08/06 Python
Python Tkinter GUI编程入门介绍
2015/03/10 Python
整理Python 常用string函数(收藏)
2016/05/30 Python
Python读取图片为16进制表示简单代码
2018/01/19 Python
Python 判断 有向图 是否有环的实例讲解
2018/02/01 Python
flask应用部署到服务器的方法
2019/07/12 Python
Python字典深浅拷贝与循环方式方法详解
2020/02/09 Python
Python GUI库Tkiner使用方法代码示例
2020/11/27 Python
中国综合性网上购物商城:当当(网上卖书起家)
2016/11/16 全球购物
纪伊国屋新加坡网上书店:Kinokuniya新加坡
2017/12/29 全球购物
党校个人自我鉴定范文
2014/03/28 职场文书
青春奉献演讲稿
2014/05/08 职场文书
语文教研活动总结
2014/07/02 职场文书
大学生求职自荐信
2015/03/24 职场文书
遗失证明范文
2015/06/19 职场文书
学生会招新宣传语
2015/07/13 职场文书
Python+Appium新手教程
2021/04/17 Python
JavaScript原型链详解
2021/11/07 Javascript
SpringBoot详解执行过程
2022/07/15 Java/Android