Part 3, much like Part 1, is open to much interpretation. I figure that the sense of "extensible" that Dave Thomas probably meant to drive at, was "easy to add features to", most likely by making subclassing easy, and accepting code blocks, and things like that. I've been giving that some thought, and it makes my head hurt. :-)
So for now, I'm going to "creatively misinterpret" it as "flexible" and "easy to put to many different uses by accepting a number of different ways it can do the job". Here is my extensible flexible version:
#! /usr/bin/ruby # Dave Thomas Code Kata #8: Conflicting Objectives # See http://codekata.pragprog.com/2007/01/kata_eight_conf.html # Solution by Dave Aronson # version 3: make it extensible # part A: creatively misinterpret "extensible" as "flexible" :-) # IDEA to make it more extensible, tho MUCH slower: # ability to split into larger # of parts? # could mitigate by also allowing minimum part length. def make_word_lists file_name, case_sensitive, max_part_len, min_part_len long_words = [] short_word_lists = [] (min_part_len .. max_part_len).each { |len| short_word_lists[len] = {} } max_len = min_part_len + max_part_len File.new(file_name, 'r').each_line do |line| word = line.chomp len = word.length word.downcase! if not case_sensitive if len == max_len then long_words << word elsif min_part_len <= len and len <= max_part_len short_word_lists[len][word] = nil end end return [long_words, short_word_lists] end def find_combos long_words, short_word_lists, max_part_len, min_part_len hits = [] max_len = min_part_len + max_part_len long_words.each do |word| (min_part_len .. max_part_len).each do |len| part_1 = word[0 .. len - 1] part_2 = word[len .. max_len - 1] if short_word_lists[len].has_key? part_1 and short_word_lists[max_len-len].has_key? part_2 hits << "#{part_1} + #{part_2} => #{word}" end end end hits end file_name = 'conflict_words.txt' max_len = 6 max_part_len = 5 min_part_len = 1 case_sensitive = false # I'll skip all the overhead of getting and parsing the above as args.... start_time = Time.now long_words, short_word_lists = make_word_lists file_name, case_sensitive, max_part_len, min_part_len hits = find_combos long_words, short_word_lists, max_part_len, min_part_len puts "hits:\n#{hits.join "\n"}\n#{hits.length} hits" puts "Running time: #{Time.now - start_time} seconds"
Okay, now I could use a bit of help from the assorted Rubyists out there. Where do you see places I could install hooks on which people can hang code blocks? What do you think would ease subclassing to change the behavior? Or do you think that's the wrong approach entirely, that I should separate the workings out, as in the Strategy or Visitor patterns? I've got too much more important stuff to do today, to give this the thought it deserves right now.
No comments:
Post a Comment
Note: Only a member of this blog may post a comment.