2013-08-04 71 views
5

我知道發送帶有參數的字符串或符號,而instance_eval帶有字符串或塊,並且它們的差異在給定接收者時可能是明顯的。send和instance_eval之間的Ruby差異?

我的問題是'下引擎蓋'的區別在於下面的例子嗎?

1234.send 'to_s'    # '1234' 
1234.instance_eval 'to_s'  # '1234' 

回答

7

fine manual

發送(符號[,ARGS ...])→OBJ
發送(字符串[,ARGS ...])→OBJ

調用標識標識的方法,將其傳遞給指定的任何參數。 [...]當方法由字符串標識時,字符串被轉換爲符號。

instance_eval

instance_eval的(字符串[,文件名[,LINENO]])→OBJ
instance_eval的{| |塊}→obj

在接收器的上下文內(obj)評估包含Ruby源代碼或給定塊的字符串。爲了設置上下文,當代碼正在執行時,變量self被設置爲obj,給出訪問obj的實例變量的代碼。

所以send執行的方法,而instance_eval執行代碼的任意塊(作爲一個字符串或塊)與self設置爲你在調用instance_eval的對象。

在你的情況,沒有太大的區別,因爲你交給instance_eval的字符串只是一種方法。主要區別在於,任何人閱讀您的代碼(包括您在六個月內)都會想知道爲什麼您使用instance_eval來調用單一方法。

您可能也有興趣Object#public_sendBasicObject#__send__

+1

好,我已經想知道爲什麼我有'instance_eval'的單一方法。 –

5

不管你可以用send做的是那的instance_eval一個子集。即,send的參數必須是單個方法(及其參數),而instance_method的參數是任意代碼。所以無論何時你有send,你都可以用instance_eval來重寫,但反之亦然。

然而,performancewise,sendinstance_eval快得多,因爲沒有執行send,而instance_eval需要解析整個論點不需要額外的解析。

在你的例子中,結果將是相同的,但第一個將運行得更快。

+1

好的總結,我得到了關於表現的獎金! –