Created
March 11, 2012 20:07
-
-
Save kennym/2017971 to your computer and use it in GitHub Desktop.
Secret Santa solution
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
http://www.rubyquiz.com/quiz2.html |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
# Secret Santas | |
# Sample format of a name list: | |
# Luke Skywalker <luke@theforce.net> | |
# Leia Skywalker <leia@therebellion.org> | |
# Toula Portokalos <toula@manhunter.org> | |
# Gus Portokalos <gus@weareallfruit.net> | |
# Bruce Wayne <bruce@imbatman.com> | |
# Virgil Brigman <virgil@rigworkersunion.org> | |
# Lindsey Brigman <lindsey@iseealiens.net> | |
# Your script should then choose a Secret Santa for every name in the list. Obviously, a person cannot be their own | |
# Secret Santa. In addition, my friends no longer allow people in the same family to be Santas for each other and your | |
# script should take this into account. | |
# Output is obvious. E-mail the Santa and tell them who their person is. | |
require 'pp' | |
class Array | |
def random | |
shuffle.first | |
end | |
end | |
class SecretSanta | |
def initialize(person_list, parse_list) | |
if parse_list | |
@persons = parse_person_list(person_list) | |
else | |
@persons = person_list | |
end | |
@persons_with_santas = persons_with_secret_santas | |
end | |
def parse_person_list(person_list) | |
persons = [] | |
person_list.each do |person| | |
person = person.scan(/^(\w*)\s(\w*)\s*(\S*)/) | |
persons.push person | |
end | |
return persons | |
end | |
def remove_family_members(person, persons) | |
[persons].collect{ |i| i if i[1] != person[1] }.compact | |
end | |
def santa_options_for_person(person) | |
persons = @persons.dup | |
persons.delete person | |
pp persons | |
persons = remove_family_members(person, persons) | |
return persons[0] | |
end | |
def pick_santa_from_options(options) | |
santa = options.random | |
return santa[0] | |
end | |
def persons_with_secret_santas | |
persons_with_secret_santas = [] | |
@persons.each do |person| | |
options = santa_options_for_person(person) | |
santa = pick_santa_from_options(options) | |
persons_with_secret_santas.push([].push(person[0], santa[0])) | |
end | |
return persons_with_secret_santas | |
end | |
def announce_person_with_santa | |
@persons_with_santas.each do |person, santa| | |
puts "The santa of #{person[0] + " " + person[1]} is #{santa[0] + " " + santa[1]}" | |
end | |
end | |
end | |
def main | |
list = [] | |
name_list_file = "name_list" if ARGV[0].nil? | |
begin | |
file = File.new(name_list_file, "r") | |
while (line = file.gets) | |
list.push line | |
end | |
file.close | |
rescue Exception => e | |
puts "Exception: #{e}" | |
e | |
end | |
secret_santa = SecretSanta.new(list, true) | |
secret_santa.announce_person_with_santa | |
end | |
main() |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
load "secret_santa.rb" | |
require "test/unit" | |
class TestSecretSanta < Test::Unit::TestCase | |
def setup | |
@persons = [["Luke", "Skywalker", "<luke@theforce.net>"], | |
["Leia", "Skywalker", "<leia@therebellion.org>"], | |
["Toula", "Portokalos", "<toula@manhunter.org>"], | |
["Gus", "Portokalos", "<gus@weareallfruit.net>"], | |
["Bruce", "Wayne", "<bruce@imbatman.com>"], | |
["Virgil", "Brigman", "<virgil@rigworkersunion.org>"], | |
["Lindsey", "Brigman", "<lindsey@iseealiens.net>"]] | |
@instance = SecretSanta.new(@persons, false) | |
end | |
def test_person_is_not_their_own_santa | |
person = @persons.sample | |
options = @instance.santa_options_for_person(person) | |
assert !options.include?(person) | |
end | |
def test_santa_is_not_in_own_family | |
person = @persons.sample | |
options = @instance.remove_family_members(person, @persons) | |
options.delete person | |
family_persons = @persons.collect{|x| x if x[1] != person[1]}.compact | |
pp options[0].size | |
puts family_persons.size | |
assert options.size == family_persons.size, "Sizes aren't the same" | |
assert options == family_persons | |
end | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment