2012-05-09 119 views
2

我正在調試和升級一些遺留的PHP和JavaScript代碼,並且發現了一些我無法擺脫的eval()函數。來自桌面編程環境,編譯語言如C/C++我從來沒有在javascript中使用eval()函數,主要是因爲我不知道它的存在。我一直在使用Google,並從所有我讀過的內容中瞭解到,eval()會評估字符串,就像它是合法的JavaScript代碼並執行它一樣。我已經設法擺脫了用於訪問動態屬性和解碼JSON對象的eval()函數,但是有一個相當先進(和模糊)的類定義,它使用了eval(),我沒有能夠擊敗。eval()和全局範圍

樣品的編號:

function Ddl(N) { 
    this.lyr = document.getElementById(N); 
    this.obj = N+"DDL_Lyr"; 
    eval(this.obj+"=this"); 
    this.lyr.setAttribute("onchange", this.obj+".onChange();"); 
} 

此函數是一個對象的構造。 DDL對象在網頁中使用:

ddl_name = new Ddl('id_of_select'); 
ddl_name.onChange = event_function; 

對於這一切,我知道,eval(this.obj + "=this")應該是一樣的this.obj = this;但隨後onchange事件功能event_function不被解僱。我一直無法猜測爲什麼使用螢火蟲。如果我使用this.obj = this,我可以看到this.obj的值從id_of_selectDDL_Lyr更改爲一個指向DDL對象的指針,所以我可以確定setAttribute失敗的原因,但是使用eval()函數this.obj並不會將代碼反映爲代碼被執行,它始終保持爲'id_of_selectDDL_Lyr',但它的做法是,因爲如果我將它註釋掉,onchange事件不會被觸發。

我懷疑它可能與本地或全局範圍有關,因爲我讀過eval()調用在不同的範圍內執行,但我不知道如何刪除它,也不知道如何替換eval ()與正常的JavaScript代碼。

+0

看起來像某種形式的對象的與平變化的另外的結合克隆event.Take看看這個討論:http://stackoverflow.com/問題/ 122102 /什麼是最有效的方法克隆一個JavaScript對象 – primavera133

+0

你試過'this.obj = window'嗎?如果你的'onChange()'函數在全局範圍內,你不需要btw。 –

+0

據我所見,eval可以用'window [this.obj] = this'替換,但我建議你先用console.log先記錄一些示例數據,以確認沒有意外的行爲。 – scragar

回答

1

認爲這個代碼是等價的:

function Ddl(N) { 
    var self = this; 
    this.lyr = document.getElementById(N); 
    this.obj = N + "DDL_Lyr"; 
    window[this.obj] = this; 
    this.lyr.onchange = function() { 
     self.onChange(); 
    }; 
} 

eval沒有說this.obj = this,它創建一個新的全球變量與 「N + DDL_Lyr」(其中N是可變的)。

+0

只有當'this.obj'中的字符串值與全局範圍中的變量名稱相同時,這才相當...該變量可能位於不是全局範圍的外部範圍中。 –

+0

@GGG它_could_,但我不認爲它是,在這種情況下。 – Alnitak

+0

我也不這麼認爲,但OP應該確定。 –

-1

變化

this.lyr.setAttribute("onchange", this.obj+".onChange();"); 

this.lyr.onchange = this.obj+".onChange();"; 
+2

AFAIK不起作用 - 設置'onchange'屬性時,您必須提供函數引用,而不是字符串。 – Alnitak