Thursday, April 3, 2014

Changes 4/3/14

Ruby:

  • Added more functionality to the block variables I was working with yesterday.  The block I ended up with [See Code 1] worked well and had proper error handling, and was tested with a test driven development in mind.  For example, 
  • block.call nil #=> error: ""
    block.call "a" #=> error: "a"
    puts block.call 2 #=> 4
    block.call %w[cat dog banana] #=> [error: "cat", error: "dog", error: "banana"]
    block.call (0..10) #=> [0, 1, 4, 9, 16, 25, 36, 49, 64, 81, 100] 
    
    
  • The block could also be passed as a variable, ie
    numbers = (0..5) # a range of numbers from 0 to 5
    block_flex_better.call(numbers) #=> [0, 1, 4, 9, 16, 25]
    numbers.map &block_flex_better #=> [0, 1, 4, 9, 16, 25]
    
  • The two statements are equivalent.  In the first, the enumerable is traversed within the block.  In the second, the elements in the enumerable are traversed by the map function and each element in the enumerable is passed to the block for operating on.
  • The & prefix before block_flex_better in the 2nd statement indicates that it is a block.
  • If you are unfamiliar with ruby, the %w[cat dog banana] is shorthand for ["cat", "dog", "banana"]
  • However, Kevin recommended that as these blocks grow more complex, they be split into their own classes.  He also said that it is bad practice in ruby to have a boolean flag as an argument, because a programmer then needs to go into the code to see what the flag does.

Code:

  1. block_flex_better = lambda do |arg, join=false| # arguments passed to the block
      final_numbers = nil
    
      # Takes some variable and attempts to square it
      operation = lambda do |num|
        if num.respond_to? "**" # Exponent notation in ruby
          num**2
        else
          "error: \"#{num.to_s}\"" # If num cannot have exponents applied 
        end
      end
    
      if arg.respond_to? "map" # If the argument is some sort of enumerable
        final_numbers = arg.map &operation
      else # If the argument is a non-enumerable (such as a fixnum)
        final_numbers = operation.call(arg)
      end
      join ? final_numbers.join(", ") : final_numbers # For convenience, a join can be applied automatically 
                                                      # by setting the join boolean to true.
    end

No comments:

Post a Comment