2014-04-06 26 views
0

一些誤解比方說,我有以下的代碼塊:使用陣列#地圖方法

arr = ['a','b','c'] 
arr.map {|item| item <<'1'} #=> ['a1','b1','c1'] 
arr #=> ['a1','b1','c1'] 

爲什麼Array#map變化的陣列?它只應該創建一個新的。當我在塊中使用+而不是<<時,它按預期工作。 Array#each更改數組本身,還是它只遍歷它並返回自身?

回答

4

我的問題是:爲什麼map更改數組?它只應該創造新的。

map不改變Array。但<<更改Array中的String

參見the documentation for String#<<

str << obj → str 

追加-串接給定的對象到str

雖然沒有明確提及它,代碼例子清楚地表明<<變異它的接收器:

a = "hello " 
a << "world" #=> "hello world" 
a.concat(33) #=> "hello world!" 

這很奇怪,因爲當我使用+運營商在塊insted的的<<它按預期工作。

+不會更改Array中的String s。

the documentation for String#+

str + other_str → new_str 

級聯,返回包含other_str連接起來以strString

請注意它是如何表示「新String」並且返回值爲new_str

而我的第二個問題:Array#each更改數組本身或它只是迭代數組並返回自己?

Array#each不改變Array。但當然,在阻止傳遞給Array#each可能會或可能不會改變個別元素Array

arr = %w[a b c] 
arr.map(&:object_id)   #=> an array of three large numbers 
arr.each {|item| item <<'1' } #=> ['a1', 'b1', 'c1'] 
arr.map(&:object_id)   #=> an array of the same three large numbers 

正如你所看到的,Array#each沒有改變Array:它仍然是相同的Array與相同的三個要素。

2

使用mapeach使得外部陣列上的差異(map將返回一個新的數組,each將返回原來的數組),但它不會做什麼字符串數組包含差異;在任何一種情況下,數組中包含的字符串都將被修改爲原始字符串。