标签:
通过实例对象作为参数传入调用构造函数对象的apply方法,
以使实例对象作为环境对象在作为一个普通函数的构造函数中执行,
构造函数的属性会覆盖到实例对象上,从而实现实例对象的属性扩展。
var tag = "global";
function say(){
for(var args = "", i = 0; i < arguments.length; ++i)
args += arguments[i] + ",";
console.log(this.tag + ": " + args);
}
var obj = {
tag: "obj",
sayObj: function(){
console.log(this.tag);
}
};
/**apply接受环境对象和数组参数;call接受环境对象和打散的数组参数*/
say.apply(obj, [1, 3, 7, 11]);//obj: 1,3,7,11,
say.call(obj, 2, 4, [8, 14]);//obj: 2,4,8,14,
say();//global
/**obj对象内部的this还是指向Global的,对象内部的函数的this才会指向这个对象*/
//obj.say(); //Uncaught TypeError: obj.say is not a function
obj.sayObj(); //obj
var x = {
name: "x",
sayX: function(){
console.log("x:" + this.name);
}
};
var y = {
name: "y"
};
/**调用的x对象的的sayX打印出x:x*/
x.sayX(); //x:x
/**普通的对象x上并没有apply方法以供调用*/
//x.apply(y); //error: x.apply is not a function
/**函数x.sayX在y对象的环境中执行,打印出x:y*/
x.sayX.apply(y); //x:y
/**在y中扩展的是sayX函数下的属性,而不是sayX本身*/
//y.sayX(); //error: y.sayX is not a function
function X(){
this.name = "x";
this.age = 11;
this.say = function(){
console.log(this.name);
}
}
function Y(){
this.name = "y";
this.color = "black";
}
/**调用构造函数X返回一个实例x*/
var x = new X();
x.say(); //x
console.log(x); //X {name: "x", age: 11, say: function()}
/**用函数对象X中的属性扩展对象y*/
var y = new Y();
console.log(y); //Y {name: "y", color: "black"}
X.apply(y);
console.log(y); //Y {name: "x", color: "black", age: 11, say: function()}
/**函数X在对象环境y中执行把name赋值为X中的值x*/
y.say(); //x
y.name = "y";
y.say(); //y
var name = "global";
var obj = {
name: "obj",
callName: function(){this.foo = function(){
console.log("欺骗了IDE");
};
console.log(this.name);
}
};
obj.callName(); //obj
/**当不传参数给apply时,默认全局环境作为第一个参数;同时全局也会获得原始环境中的属性*/
obj.callName.apply();
/**在原来的obj环境中运行函数,搜索到最近的值还是obj的属性name的值obj*/
obj.callName(); //obj
/**
* 当没有执行上面的apply时,是会报错的;当然也不建议这样做
* Uncaught ReferenceError: foo is not defined
* 在执行apply时,运行了this.foo=...,这里的this在运行时指的是全局环境
* 所以在下面执行foo时,会打印出
*/
foo();//欺骗了IDE
/**
* 在通过圆括号把函数声明转化为函数表达式并立刻执行它
* 这个函数内部的环境就是这个函数的环境,从而避免了全局变量冲突 */(function(){var person = {
name: "Ameki",
age: 18,
sayHi: function(){
alert("Hello, " + this.name);
}
};for(var prop in person){
console.log(prop + ", " + person[prop]);
}
})();
/* name, Ameki
age, 18
sayHi, function (){
alert("Hello, " + this.name);
}
*/
如果你觉得本文对你有帮助,请点击右下方的推荐按钮,这样就可以让更多的小伙伴看到它了。
本文地址:http://www.cnblogs.com/kodoyang/p/Javascript_FunctionApply_ExtendEnvironmentObject.html
雨木阳子
2015年9月22日
标签:
原文地址:http://my.oschina.net/kodoyang/blog/509428