RSPEC测试阵列中的最短字符串

时间:2014-12-03 02:17:34

标签: ruby-on-rails ruby rspec

我知道我可以用哈希方法做到这一点,但我不明白为什么我的方法没有通过" shuffle示例"

这是我得到的错误。

1) shortest_string returns the shortest string regardless of ordering                                                                                              
     Failure/Error: expect(shortest_string(array)).to eq 'a'                                                                                                         

   expected: "a"                                                                                                                                                 
        got: "aaa"                                                                                                                                               

   (compared using ==)                                       

# ./shortest-string-spec.rb:25:in `block (2 levels) in <top (required)>

my_solution.rb

def shortest_string(arr)
  if arr.empty?
    nil
  else
    min_length = arr[0].length
    result = arr[0]
    arr.each do |element|
      element.length < min_length ? (result = element) : result
    end
    result
  end 
end

RSPEC

require_relative "my_solution"

describe 'shortest_string' do
  it "returns nil when the array is empty ([])" do
    expect(shortest_string([])).to be_nil
  end

  it "returns '' when that is the only element in the array" do
    expect(shortest_string([''])).to eq ''
  end

  it "returns 'cat' when that is the only element in the array" do
    expect(shortest_string(['cat'])).to eq 'cat'
  end

  it "returns the 'zzzzzzz' with the example array" do
    expect(shortest_string(['cat', 'zzzzzzz', 'apples'])).to eq 'cat'
  end

  it "returns the shortest string regardless of ordering" do
    # This creates an array containing ['a', 'aa', ...]
    # up to 10 characters long, but randomly ordered
    array = Array.new(10) { |i| 'a' * (i + 1) }.shuffle

    expect(shortest_string(array)).to eq 'a'
  end
end

UPDATE,

我怎么能这样做?

element.length&lt; min_length? (result = element):结果? (min_length = element.length)? MIN_LENGTH

2 个答案:

答案 0 :(得分:1)

当您找到新的最低值时,您不会重置min_length,因此它仍然认为 小于arr[0].length的任何内容都应该通过。

示例:

array = ["aaa", "a", "aa"]

该数组的第二个和第三个元素小于min_length,因为您设置了result = element,它会在aa方法的最终传递中捕获each

您可以通过执行以下操作来解决此问题:

def shortest_string(arr)
  if arr.empty?
    nil
  else
    min_length = arr[0].length
    result = arr[0]
    arr.each do |element|
      if element.length < min_length 
        result = element
        min_length = element.length
      end
    end
    result
  end 
end

答案 1 :(得分:1)

您可以使用Enumerable#max_by

array = ["aaa", "a", "aa"]
array.max_by { |x| -x.length }
# => "a" 

[].max_by { |x| -x.length }
# => nil