2017-03-08 47 views
0

我有一個管理配置的類(本地保存爲JSON),並且我寫了一個方法來將配置從一個文件複製到另一個文件。這兩個JSON文件都作爲散列加載到實例變量中(分別爲@local@repository)。我遇到了一些奇怪的行爲,其中在一個散列上設置密鑰會覆蓋另一個散列中相同密鑰的值。我已將問題縮小到下面的代碼段的第14行。第12行的我的puts聲明將@repository[brand][:branches][branch]顯示爲包含數據的非空哈希,而第21行的我的puts聲明顯示@repository[brand][:branches][branch]爲空哈希。將一個散列拷貝到另一個時奇怪的行爲

def copy(brand, branch = nil) 
    brand = brand.to_sym 
    branch = branch.to_sym 

    if branch.nil? 
     if @local[:repository].has_key?(brand) 
      @local[:repository][brand].deep_merge(@repository[brand]) 
     else 
      @local[:repository][brand] = @repository[brand] 
     end 
    else 
     puts @repository[brand][:branches][branch] 
     unless @local[:repository].has_key?(brand) 
      @local[:repository][brand] = @repository[brand] 
      @local[:repository][brand][:branches] = Hash.new 
     end 

     unless @local[:repository][brand][:branches].has_key?(branch) 
      @local[:repository][brand][:branches][branch] = Hash.new 
     end 
     puts @repository[brand][:branches][branch] 
     @local[:repository][brand][:branches][branch].deep_merge(@repository[brand][:branches][branch]) 
    end 

    self.write(CONFIG_FILE, @local) 
end 

如果我改變線14 @local[:repository][brand] = Hash.new,上線21哈希值不再是空的,其實是在預期值。一個關鍵的問題是@local[:repository]中的brand鍵還不存在。

任何人都可以點亮這裏發生的一切嗎?

+0

這與y無關我們的實際問題,但你應該閱讀如何在RoR中使用'unless'。 http://www.railstips.org/blog/archives/2008/12/01/unless-the-abused-ruby-conditional/並清理那個if語句,我沒有機會理解正在發生的事情。 – bork

+0

我其實已經閱讀過這個頁面:除非,據我所知,我正在使用它,他們是如何推薦的。我沒有檢查任何零,也沒有我的除非有多個條件的除非陳述。而且,在這兩種情況下,我都沒有檢查其他情況。所以,除非我看起來更清潔。 至於'if'語句正在清理,請注意說明一下嗎? – sluther

+1

這段代碼中的問題在哪裏?你剛剛發佈了一段代碼,但它沒有解釋預期的結果,也沒有解釋問題的位置。 http://stackoverflow.com/help/mcve – Casper

回答

2

罪魁禍首在於這條線(其中使用兩次):

@local[:repository][brand] = @repository[brand] 

這沒有駐留在@repository[brand]哈希的副本。
讓我們拆分了一下,讓我們可以更清楚地談論它:

brand_detail = @repository[brand] 
local_repo = @local[:repository] 
local_repo[brand] = brand_detail 

第三條語句後,local_repo[brand]將不包含brand_details哈希的副本而是一個參考該散列。所以現在所有這些線都會有相同的效果;他們將所有修改相同的散列比如:

  • brand_detail[:branches] = 3
  • local_repo[brand][:branches] = 3
  • @repository[brand][:branches] = 3

你應該能夠明確地添加,而不是使用dup參考副本來規避這樣的:

@local[:repository][brand] = @repository[brand].dup 
+0

謝謝。這解決了我的問題。 – sluther

相關問題