When I have time I like to take on a challenge at codewars.
Until now I used test/unit
to do my unit testing but I would like to use Rspec
now without changing my way of working. These are small methods/files/tests so I like to keep everything together in one script.
I run almost all of my code using Sublime Text and get the result in a window at the bottom of the editor.
Here my working test/unit
example
require 'test/unit'
def anagrams(word, words)
words.select { |w| w.chars.sort == word.chars.sort }
end
class MyTest < Test::Unit::TestCase
def test_fail
assert_equal(['aabb', 'bbaa'], anagrams('abba', ['aabb', 'abcd', 'bbaa', 'dada']) )
assert_equal(['carer', 'racer'], anagrams('racer', ['crazer', 'carer', 'racar', 'caers', 'racer']) )
assert_equal([], anagrams('laser', ['lazing', 'lazy', 'lacer']) )
end
end
This gives in Sublime the following output
Loaded suite C:/Users/.../codewars/anagram
Started
.
Finished in 0.001 seconds.
------
1 tests, 3 assertions, 0 failures, 0 errors, 0 pendings, 0 omissions, 0 notifications
100% passed
------
1000.00 tests/s, 3000.00 assertions/s
[Finished in 0.3s]
And here what I tried for Rspec
require 'rspec'
describe "Anagrams" do
def anagrams(word, words)
words.select { |w| w.chars.sort == word.chars.sort }
end
it "should only match the anagrams" do
anagrams('abba', ['aabb', 'abcd', 'bbaa', 'dada']) == ['aabb', 'bbaa']
end
end
In Sublime text, I get no output, just a empty black window with the time it took to execute the script, if I use the console and run rspec anagram.rb
I get
.
Finished in 0.001 seconds (files took 0.10601 seconds to load)
1 example, 0 failures
How do I have my code and test in the same file and do the test just by running the script in my Sublime Text editor (and get the output) and how could I better rephrase this test ?
You just need to tell the RSpec::Core::Runner
to run your spec.
Adding RSpec::Core::Runner.run([$__FILE__])
at the end of your fill should work.
Updated code:
require 'rspec'
describe "Anagrams" do
def anagrams(word, words)
words.select { |w| w.chars.sort == word.chars.sort }
end
it "should only match the anagrams" do
anagrams('abba', ['aabb', 'abcd', 'bbaa', 'dada']) == ['aabb', 'bbaa']
end
end
RSpec::Core::Runner.run([$__FILE__])
I don't know what magic you used for sublime text to auto run your unit tests. What I can answer is how to phrase the test better.
require 'rspec'
def anagrams(word, words)
words.select { |w| w.chars.sort == word.chars.sort }
end
RSpec.describe "Anagrams" do
it "matches words that are anagrams" do
# 2 different ways to do this
expect(anagrams('abba', ['aabb', 'abcd', 'bbaa', 'dada'])).to match_array(['aabb', 'bbaa'])
expect(anagrams('abba', ['aabb', 'abcd', 'bbaa', 'dada'])).to contain_exactly('aabb', 'bbaa')
end
end
match_array
& contain_exactly
are identical, except that match_array needs 1 parameter: array and contain exactly needs no array, instead you list all memebers of array.
https://www.relishapp.com/rspec/rspec-expectations/docs/built-in-matchers/contain-exactly-matcher
You could also break this into 2 or more specs if you want to. I'd do that if logic was more complicated. Going to do it here anyway so you can see more examples of rspec messages. Using should in spec name is no longer recommended.
RSpec.describe "Anagrams" do
it "when no annagrams found returns empty array" do
expect(anagrams('abba', ['abcd', 'dada'])).to eq([])
end
it "recognizes itself as annagram" do
expect(anagrams('abba', ['abba'])).to eq(['abba'])
end
it "returns array containing words that are anagrams" do
expect(anagrams('abba', ['aabb', 'abcd', 'bbaa', 'dada'])).to contain_exactly('aabb', 'bbaa')
end
end
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With