Manasi Salvi

TDD Lesson 4

Exercise 49 of Learn Ruby the Hard Way you’re required to write the tests based on the code given to you. After working through the last exercise, this somehow made a lot more sense.

I used the Ruby docs Module on Test::Unit::Assertions for this exercise. I stuck to the assert_equal and assert_not_equal methods to test whether the ‘expected was equal to actual’ or ‘not equal to actual’ respectively and the assert_raise method to raise an exception.

The assert_raise method was tricky to work with initially as there weren’t many beginner level friendly code examples but with a bit of trial and error we got there.

The code provided in the book also required a bit of tweaking so the test file would run. Here are some examples of my test code for the exercise 49.

parsing a subject parser.rb

def self.parse_subject(word_list)
  self.skip(word_list, 'stop')
  next_word = peek(word_list)

      if next_word == 'noun'
        return self.match(word_list, 'noun')
      elsif next_word == 'verb'
        return ['noun', 'player']
      else
        raise ParserError.new("Expected a verb next.")
      end
  end

test_parser.rb

def test_parse_subject()
	assert_equal((Sentence.parse_subject([["noun", "princess"], ["verb", "eat"]])), ["noun", "princess"], ["noun", "player"])
	assert_equal((Sentence.parse_subject([["verb", "eat"],["noun", "princess"]])), ["noun", "player"])
	assert_equal((Sentence.parse_subject([["noun", "princess"], ["stop", "the"]])), ["noun", "princess"])
	assert_not_equal((Sentence.parse_subject([["verb", "eat"], ["noun", "princess"]])), ["verb", "eat"], ["verb", "player"])
	assert_raise ParserError do 
		Sentence.parse_subject(nil)
	end
	assert_raise ParserError do 
		Sentence.parse_subject(["direction", "north"])
	end
end

TDD Lesson 3

The next challenge was writing the code for the test: test_lexicon.rb

	def test_numbers()
	    assert_equal(Lexicon.scan("1234"), [['number', 1234]])
	    result = Lexicon.scan("3 91234")
	    assert_equal(result, [['number', 3],
	           ['number', 91234]])
	end
 

The test requires conversion the scanned input in the form of a sentence into numbers. This required the use of exceptions by using the begin-rescue statement. Exceptions indicate that something has gone wrong and therefore throws an error - in this case an Argument Error. Before using the exceptions I did try to put the numbers into the hash (as for the rest of the word types) and looping over this hash however this wouldn’t work because it would try to convert some of the words into numbers and throw back an error. This would also be impractical as it wouldn’t be able to handle every possible combination of numbers e.g. the input could look like [‘12345’, ‘0’, ‘12’] and so on.

With the use of the exceptions I came up with the folowing code:

 	def self.convert_integer(word) #scan self and convert to integer - this becomes the number variable
  		number = /[0-9]/ #define the number as an integer between 0-9
  		begin
    		return Integer(word) 
  		rescue  #Argument error thrown when the word is not an integer
    		return nil
  		end
	end