2012-08-07 72 views
3

最近我開始學習Ruby,並且我正在試驗Ruby如何在單個對象上調用方法。但是,下面的代碼塊卡住了我一下,因爲我沒有意識到它實際上是如何工作的,以通過方法語法調用的操作符方法的優先級

a = 4 
b = -3 
c = 2 

puts a*b-c      # operator precedence preserved 
puts a . * b . - c    # operator precedence not preserved 
puts a.send(:*, b).send(:-, c) # operator precedence preserved 
puts a-b*c      # operator precedence preserved 
puts a . - b . * c    # operator precedence preserved 
puts a.send(:-, b).send(:*, c) # operator precedence not preserved 

輸出:

-14 
-20  
-14 
10 
10 
14 

任何人都能夠解釋的運算符優先級如何工作的嗎?我認爲每個部分中的所有三種語法應該反映相同的含義。如果這個問題已經被詢問或解釋了,我先道歉。

+7

我不明白你的問題。在示例2,3,5和6中,您不使用操作符語法,而是使用方法語法,因此運算符優先級甚至不起作用。 – 2012-08-07 02:40:34

+1

這是否意味着我們不能在Ruby中使用操作符語法和方法語法(反之亦然)?我想說例子2和3或5和6解釋相同的意思。你能好好解釋這個嗎?謝謝。 – joarderm 2012-08-07 02:53:30

+4

@JoarderKamal所有的方法調用總是具有相同的優先級,而運算符可能有不同的優先級。 – 2012-08-07 02:58:01

回答

5

運算符優先級僅適用於使用運算符時。所有這些例子:

puts a . * b . - c    # operator precedence not preserved 
puts a.send(:*, b).send(:-, c) # operator precedence preserved 
puts a . - b . * c    # operator precedence preserved 
puts a.send(:-, b).send(:*, c) # operator precedence not preserved 

是直接的方法調用,並且發生在任順序錯誤或正確的順序相比,其對應的運營商。

括號能否讓它更清楚?

puts a.*(b.-(c))    # .- called first, .* with the return value of .- 
puts a.send(:*, b).send(:-, c) # .* called first, .- with the return value of .* 
puts a.-(b.*(c))    # .* called first, .- with the return value of .* 
puts a.send(:-, b).send(:*, c) # .- called first, .* with the return value of .- 
+0

這是否意味着,當我們想要將操作符語法完全轉換爲方法調用語法時,我們必須自己使用適當的括號,否則Ruby解釋器將無法通過它自己識別操作符優先級?對.. – joarderm 2012-08-07 03:08:04

+0

@JoarderKamal:你不一定非要用括號;只要將它們重新編寫爲從右到左。 (但是......你爲什麼要那樣做?) – Ryan 2012-08-07 03:11:36

+0

因爲......我只是做這個 把一個*不保留B.-C#運算符優先級 把一個*(B).-(三)#運算符優先級保留 輸出:。 -20 - 14 這意味着沒有任何括號表達式工作不同。 – joarderm 2012-08-07 03:18:45

0

只有示例1和4遵從算術運算符優先級,因爲只有示例1和4將運算符稱爲運算符。

示例3和6都調用send方法,因此它們的行爲與其他任何方法調用一樣。他們去從左至右,就像當你寫一個複雜的班輪上的數據的集合,像這樣發生了什麼:

somearray.select{|x| somecondition(x)}.map{|x| somefunction(x)}.each{|x| puts x} 

唯一令人困惑的有例2和5,這些方法的訣竅是你可以瞭解發生了什麼,如果你刪除週期的空間。然後你得到:

puts a.* b.- c 
puts a.- b.* c 

現在,應該很明顯,首先有一個方法調用b,應用一些運算符,將c作爲參數。這會返回一些結果。該結果被用作a上的運算符調用的參數。這是put的結果。換句話說,這些行從右到左評估,並且這些語句相當於

puts(a.*(b.-(c))) 
puts(a.-(b.*(c))) 
+0

如果是這樣的話,那麼明顯的例子2和3或例子5和6解釋相同的含義。那麼乳清他們沒有產生相同的結果?它應該是-20例如2和3或10例如5和6. – joarderm 2012-08-07 03:12:57

+0

@JoarderKamal。它們意思不一樣。一個從右到左,另一個從左到右。我編輯瞭解釋更好。 – 2012-08-07 13:05:39