2011-01-18 50 views
15

給未來讀者的提示:RSpec認爲你的Hashes不等於?一個可能是一個OrderedHash,但是從常規的RSpec輸出你不能說。這是促成這篇文章的問題。用於匹配Hashes的RSpec2匹配器是否存在?

原題:

假設我有一個規範,我想測試的方法生成相應的哈希值。

it 'should generate the Hash correctly' do 
    expected = {:foo => 1, 'baz' => 2} 
    subject.some_method_that_should_generate_the_hash.should == expected 
end 

這經常會失敗,因爲具有相同鍵值對的不同Hashes可能以不同的順序返回它們的對。結果如下:

Failure/Error: subject.some_method_that_should_generate_the_hash.should == expected 
expected: {:foo => 1, 'baz' => 2}, 
    got: {'baz' => 2, :foo => 1} 

對於數組,這可以使用=〜運算符來解決。但是,這對於Hashes無效。現在,我已經使用

it 'should generate the Hash correctly' do 
    expected = {:foo => 1, 'baz' => 2} 
    subject.some_method_that_should_generate_the_hash.each {|k,v| 
    v.should == expected[k] 
    } 
end 

但這似乎不必要的冗長。我希望有一個明顯的解決方案。我忽略文檔中的某些內容還是RSpec沒有適當的匹配哈希平等的匹配?

回答

17
describe 'Hash' do 
    let(:x) { { :a => 1, :b => 2 } } 
    let(:y) { { :b => 2, :a => 1 } } 

    it "should be equal with ==" do 
    x.should == y 
    end 
end 

通行證。我不確定你的具體情況是怎麼回事。你可以分享一些失敗的例子嗎?

編程Ruby有這樣一段話:

平等 - 兩個散列相等,如果 它們具有相同的默認值,它們 包含相同的數字鍵,並 對應於每個鍵的值 第一個散列值等於(使用==)至 與 秒中相同的密鑰值。

+0

昨天晚了,我發現了這個問題:我實際上並沒有比較兩個哈希:一個在一路上變成了OrderedHash。你不能從RSpec輸出中看到這一點,我有點尷尬地說這不是我第一次陷入這個陷阱:/ – Confusion 2011-01-19 06:08:25

+3

有趣。因此,OrderedHash和Hash具有相同的鍵/值對並不相同 - 這很好理解。 – zetetic 2011-01-19 07:33:30

3

我相信eql?方法只檢查兩個散列具有相同的內容 所以IIRC在Rspec2你可以這樣做:

expected = {:foo => 1, 'baz' => 2} 
    expected.should be_eql({'baz' => 2, :foo => 1}) 

而且測試應該通過

+0

或rspec的3,`希望(X)。爲了EQL(Y )` – nruth 2016-04-27 16:18:47