eval() 函數可計算某個字串,並執行其中的的 JavaScript 代碼。
文法
eval(string)參數 描述
string 必需。要計算的字串,其中含有要計算的 JavaScript 運算式或要執行的語句。
傳回值
通過計算 string 得到的值(如果有的話)。
先來說eval的用法,內容比較簡單,熟悉的可以跳過。
eval函數接收一個參數s,如果s不是字串,則直接返回s。否則執行s語句。如果s語句執行結果是一個值,則返回此值,否則返回undefined。
需要特別注意的是對象聲明文法“{}”並不能返回一個值,需要用括弧括起來才會傳回值,簡單樣本如下:
var code1='"a" + 2'; //運算式
var code2='{a:2}'; //語句
alert(eval(code1)); //->'a2'
alert(eval(code2)); //->undefined
alert(eval('(' + code2 + ')')); //->[object Object]
無論是變數定義還是函數定義都是如此,所以如下的代碼會產生函數未定義的錯誤:
var s='function test(){return 1;}'; //一個函數定義語句
function demo2(){
eval(s);
}
demo2();
alert(test()); //->error:test is not defined
可以同時相容IE和Firefox,方法如下:
var X2={} //my namespace:)
X2.Eval=function(code){
if(!!(window.attachEvent && !window.opera)){
//ie
execScript(code);
}else{
//not ie
window.eval(code);
}
}
現在如果要想在函數內定義全域代碼,就可以通過調用X2.Eval(code)方法,一個例子如下:
var s='global';
function demo3(){
X2.Eval('var s="local"');
}
demo3();
alert(s); //->'local'
說明
該方法只接受原始字串作為參數,如果 string 參數不是原始字串,那麼該方法將不作任何改變地返回。因此請不要為 eval() 函數傳遞 String 對象來作為參數。
如果試圖覆蓋 eval 屬性或把 eval() 方法賦予另一個屬性,並通過該屬性調用它,則 ECMAScript 實現允許拋出一個 EvalError 異常。
IE 當eval遇上function的處理
情況1:eval裡沒有function,直接執行:
eval("alert('ss');");//所有瀏覽器正確均輸出
情況2:eval裡有function,function立即執行:
eval("(function(){alert('ss');})();");//所有瀏覽器正確輸出
情況3:eval裡有function,使用變數儲存function引用並調用該function:
var f=eval("(function(){alert('ss');})");
f();//IE下報錯:缺少對象 其他瀏覽器正常
當在eval定義一個function並返回給變數時,IE報錯:缺少對象。可見IE下eval裡定義的function並不能成功返回到eval外部。
解決方案:使function對象作為一個執行結果返回:
方法1:
var f=eval("(function(){ return function(){alert('ss');}})()");
f();//所有瀏覽器正確輸出
eval裡調用一個立即執行的函數,該函數執行之後返回一個function對象,此時該function對象的引用成功返回到外部變數。
方法2:
var f=eval("(false||function(){alert('ss');})");
f();//所有瀏覽器成功輸出
該方法也是jquery裡使用的方法,function作為或運算式的執行結果返回,同樣能成功解決問題。當然,運算式並不局限於上面的false||function(){},各種運算式只要能成功返回function,均可解決問題:
/* 與運算式:*/
var f=eval("(true&&function(){alert('ss');})");
f();//所有瀏覽器正常輸出
/* 三元運算式:*/
var f=eval("(true?function(){alert('ss');}:'');");
f();//所有瀏覽器正常輸出