JavaScript函数的多种定义方法与其区别是什么?
javascript和其他编程语言相比比较随意,所以javascript代码中充满各种奇葩的写法,有时雾里看花,当然,能理解各型各色的写法也是对javascript语言特性更进一步的深入理解,那么他有几种写法呢? ( function(){…} )() 这样,( function (){…} () )这样
javascript闭包 JavaScript javascript面向对象
Answers
第一种:
var sum = function(num1,num2){
return num1 + num2;
};
第二种:
function sum(num1,num2){
return num1 + num2;
}
第三种:
var sum = new Function("num1","num2","return num1 + num2");
第三种用对象的方式定义函数,前面参数为函数的参数,最后为函数体。但是需要解析传入的字符串参数,导致两次解析,所以不推荐这种方式来定义函数。
第一和第二种没太大差别。
JS的函数定义方式就两种——函数定义(function declaration, abbreviation as FD) 和 函数表达式(function expression, abbreviation as FE)
而函数表达式又分为命名与匿名两种。至于构造函数则是函数调用时操作方式与定义无关。
FD与FE的具体区别在于:
FD是在构建函数的Execution Context时会被计算并作为Activation Object的一个属性被引用,因此就出现declaration hoisting的现象。而FE则是在函数的Runtime中才被计算,而且不会作为Activation Object的一个属性被引用。
因此下面的代码在IE9+下无法引用之前的FE
(function hello(){console.log('hey, man!')})
try{
hello()
}
catch(e){
console.log(e) // hello is not defined.
}
注意:上述代码在IE8下hello可用的。
另外FD在recommendation中规定只能出现在全局块和函数块,但Chrome和FF都对此规范进行扩展,因此
if (true){
function test(){}
}
else{
function test(){}
}
是合法的。
另外new关键字实际就是
function test(){}
var t = new test()
var po = Object(), t
t = test.call(po)
if (!t) t = po
js函数有普通函数、构造函数、匿名函数,定义方式有三种,即函数声明方式、函数表达式方式、函数对象方式
1、函数声明方式:
function sum(value1, value2){
return value1 + value2;
}
2、函数表达式方法:
var sum = function(value1, value2){
return value1 + value2;
}
3、函数对象方法:
var sum = new Function('value1', 'value2', 'return value1 + value2');
区别:
三者区别几乎没有,不同的是,函数声明方式声明的函数会被解析器通过函数声明提升的过程即function declaration hoisting置于原代码数的顶部,所以即使在函数前调用该函数也可以正常使用;而函数表达式方式除了不能在声明前调用外,与函数声明方式一样;函数对象方法可以直观地理解“函数是对象,函数名是指针”这个概念,但是它会造成解析器两次解析,一次是普通的ECMAScript代码,一次是解析传入Function构造函数里的字符串,会影响js引擎性能
普通函数:
function square(x) {
return x * x;
}
console.log(square(3));
用var声明的匿名函数:
var square = (function(x) {
return x * x;
});
或者
var square = function(x) {
return x * x;
};
console.log(square(3));
匿名函数(其中(3)表示传入参数3并执行此匿名函数):
(function(x) {
return x * x;
})(3);
或者
(function(x) {
return x * x;
}(3));
抓住两个关键点很重要:
-
js中函数是引用类型;
-
函数一般执行方式:函数名+();
下面的例子帮你理解引用类型
var a = function(x,y){
console.log(x + y);
};
var b = a;
a(1,2);
b(1,2); //b,a指向同一个函数对象
//b重新赋值
b = function(x,y){
console.log(x - y);
}
a(1,2);
b(1,2);
如果还是不理解,参考下这篇文章:
javascript中的引用类型
接下来说明下函数的几种定义方式:
-
函数声明
alert(sum(1,2));
function sum(x,y){
return x + y;
}
-
函数表达式
//这段代码会报错
alert(sum(1,2));
var sum = function (x,y){
return x + y;
}
在写递归的时候可以这样写
//如果直接用sum(x-1) + sum(x-2),如果sum被改名,或者重新赋值,产生bug
var sum = function fSum(x){
if(x<=2)
return 1;
else
return fSum(x-1) + fSum(x-2);
};
alert(sum(5));
-
匿名函数
(function(x,y){
alert(x + y);
})(1,2);