猿吟鹤唳本无意,不知下有行人行

js函数带括号和不带括号的区别

先说结果

1、加了括号的代表执行完毕得到函数的结果(括号的二义性,是“函数的调用运算符”)

2、没加括号的,查看该函数的完整信息。指向函数的指针,只是传递了函数题所在的地址位置。

举例:

//demo1
function demo1() {
    var m = 3;
    alert(m);
}
function demo2() {
    var m = 55;
    alert(m);
}

var e = document.getElementById('btn'); 
   
// 点击的时候才进行执行  点击按钮“btn”后弹出3
e.addEventListener('click', demo1); 
    
// 直接就已经弹出进行了执行 弹出55    
e.addEventListener('click', demo2());

//demo2
function foo(){
 var m = 3;
return m;
}
var a = foo;
var b = foo();
console.log(a); //函数体
console.log(b);//3

其中括号的二义性。感觉像通假字,可以有俩意思。比如一个用红色墨水写的“蓝”字。这个字是什么颜色?蓝?红?

2.7.2 括号"( )"的二义性

我们来看下面语句中的括号"( )"应该是什么含义呢?

var str = typeof(123);  
var str = ('please input a string', 1000); 
第一个 typeof 看起来好像被当成了函数使用--这是否说明 typeof 为一个"内部函数"呢?而第二行代码,你相信它会成功执行并使 str"意外地"赋值为 1000 吗?括号首先可以作为语句中的词法元素。例如函数声明中的"虚拟参数表":
//声明函数时,括号用做参数表  
function foo(v1, v2) {  
//…  
} 
第二种情况,就是括号只作为"传值参数表(这有别于函数声明中的'虚拟参数表')",注意这里它并不表达函数调用的含义。目前为止,它只出现在 new 关键字的使用中:new关键字用于创建一个对象实例并负责调用该构造器函数,如果存在一对括号"( )"指示的参数表,则在调用构造器函数时传入该参数表,对此的具体分析,我们已经在"2.5.1.1使用构造器创建对象实例"中讲述过了。例如:
//构造对象时,用于传入初始化参数  
var myArray = new Array('abc', 1, true); 
接下来,它也可以在 with、for、if、while 和 do...while 等语句,以及 catch()等子句中用来作为限定表达式的词法元素:
// for语句(for…in语句类同)  
for ( initialize; test; increment )  
statement  
 
// if语句  
if ( expression )  
statement  
 
// while语句  
while ( expression )  
statement  
 
// do…while语句  
do  
statement  
while ( expression ) 
在充当 if、while 和 do...while 语句中的词法元素时,括号会有"将表达式结果转换为布尔值"的副作用(参见"5.7.3.2语句(语义)导致的类型转换")。在很多时候,语句中的括号会产生类似于"运算"这样的附加效果。

第四种情况,是括号"( )"用于强制表达式运算。这种情况下,基本含义是我们通常说的强制运算优先级。但事实上,不管有没有优先级的问题,括号总是会强制其内部的代码作为表达式运算。例如我们在这一小节开始列举的例子:

var str1 = typeof(123);  
var str2 = ('please input a string', 1000); 
在第 1 行代码中,"( )"强制 123 作为单值表达式运算,当然运算结果还是 123,于是再进行 typeof 运算。所以这里的一对括号起到了强制运算的作用。同样的道理,第 2 行代码里的一对括号也起到相同的作用,它强制两个单值表达式做连续运算,由于连续运算符","的返回值是最后一个表达式的值,因此这个结果返回了 1000。所以我们要意识到,上面的第 1 行代码并没有调用函数的意思,而第 2 行代码将使 str2 被赋值为 1000。

最后一种情况最为常见:作为函数/方法调用运算符。例如:

//有(),表明函数调用  
foo();  
//没有(),则该语句只是一个变量的返回。  
foo; 
我们一再强调:函数调用过程中的括号"( )"是运算符。也因此得出推论,当"( )"作为运算符时,它只作用于表达式运算,而不可能作用于语句。所以你只能将位于:
function foo() {  
return( 1 + 2);  
} 
这个函数内的、return 之后的括号理解成"强制表达式优先级",而不是理解成"把 return当成函数或运算符使用"。所以从代码格式化的角度上来说,在下面两种书写方法中,第二种才是正确的:

//第一种,像函数调用一样,return后无空格  
return(1 + 2);  
 
//第二种,return后置一空格  
return (1 + 2); 
基于同样的理由,无论"break (my_label)"看起来如何合理,也会被引擎识别为语法错误。因为 my_label 只是一个标签,而不是可以交给"( )"运算符处理的运算元,标签与运算元属于两个各自独立的、可重复(而不发生覆盖)的标识符系统。