Implement a program that translates from English to Pig Latin.
Pig Latin is a made-up children's language that's intended to be confusing. It obeys a few simple rules (below), but when it's spoken quickly it's really difficult for non-children (and non-native speakers) to understand.
There are a few more rules for edge cases, and there are regional variants too.
See http://en.wikipedia.org/wiki/Pig_latin for more details.
For installation and learning resources, refer to the Ruby resources page.
For running the tests provided, you will need the Minitest gem. Open a terminal window and run the following command to install minitest:
gem install minitest
If you would like color output, you can require 'minitest/pride'
in
the test file, or note the alternative instruction, below, for running
the test file.
Run the tests from the exercise directory using the following command:
ruby pig_latin_test.rb
To include color from the command line:
ruby -r minitest/pride pig_latin_test.rb
The Pig Latin exercise at Test First Teaching by Ultrasaurus https://github.com/ultrasaurus/test-first-teaching/blob/master/learn_ruby/pig_latin/
It's possible to submit an incomplete solution so you can see how others have completed the exercise.
require 'minitest/autorun'
require_relative 'pig_latin'
# Common test data version: 1.2.0 d77de78
class PigLatinTest < Minitest::Test
def test_word_beginning_with_a
# skip
assert_equal "appleay", PigLatin.translate("apple")
end
def test_word_beginning_with_e
skip
assert_equal "earay", PigLatin.translate("ear")
end
def test_word_beginning_with_i
skip
assert_equal "iglooay", PigLatin.translate("igloo")
end
def test_word_beginning_with_o
skip
assert_equal "objectay", PigLatin.translate("object")
end
def test_word_beginning_with_u
skip
assert_equal "underay", PigLatin.translate("under")
end
def test_word_beginning_with_a_vowel_and_followed_by_a_qu
skip
assert_equal "equalay", PigLatin.translate("equal")
end
def test_word_beginning_with_p
skip
assert_equal "igpay", PigLatin.translate("pig")
end
def test_word_beginning_with_k
skip
assert_equal "oalakay", PigLatin.translate("koala")
end
def test_word_beginning_with_x
skip
assert_equal "enonxay", PigLatin.translate("xenon")
end
def test_word_beginning_with_q_without_a_following_u
skip
assert_equal "atqay", PigLatin.translate("qat")
end
def test_word_beginning_with_ch
skip
assert_equal "airchay", PigLatin.translate("chair")
end
def test_word_beginning_with_qu
skip
assert_equal "eenquay", PigLatin.translate("queen")
end
def test_word_beginning_with_qu_and_a_preceding_consonant
skip
assert_equal "aresquay", PigLatin.translate("square")
end
def test_word_beginning_with_th
skip
assert_equal "erapythay", PigLatin.translate("therapy")
end
def test_word_beginning_with_thr
skip
assert_equal "ushthray", PigLatin.translate("thrush")
end
def test_word_beginning_with_sch
skip
assert_equal "oolschay", PigLatin.translate("school")
end
def test_word_beginning_with_yt
skip
assert_equal "yttriaay", PigLatin.translate("yttria")
end
def test_word_beginning_with_xr
skip
assert_equal "xrayay", PigLatin.translate("xray")
end
def test_y_is_treated_like_a_consonant_at_the_beginning_of_a_word
skip
assert_equal "ellowyay", PigLatin.translate("yellow")
end
def test_y_is_treated_like_a_vowel_at_the_end_of_a_consonant_cluster
skip
assert_equal "ythmrhay", PigLatin.translate("rhythm")
end
def test_y_as_second_letter_in_two_letter_word
skip
assert_equal "ymay", PigLatin.translate("my")
end
def test_a_whole_phrase
skip
assert_equal "ickquay astfay unray", PigLatin.translate("quick fast run")
end
end
class PigLatin
def self.translate(input)
new(input).translate
end
def initialize(input)
@words = input.split ' '
end
def translate
words.map { |word| translate_word(word) }.join ' '
end
private
attr_reader :words
def translate_word(word)
scan_word(word) + 'ay'
end
def scan_word(word)
case word
when vowel_sound
word
when consonant_followed_by_qu
beginning = word.scan(consonant_followed_by_qu).first
word.gsub!(consonant_followed_by_qu, '')
word + beginning
when consonant_cluster_y
beginning = word.scan(/^[^aeiouy]*/).first
word.gsub!(/^[^aeiouy]*/, '')
word + beginning
when consonant_sound
first = word.scan(/^#{consonant}+/).first
word.gsub(/^#{consonant}+/, '') + first
end
end
def consonant_sound
/^#{consonant}/
end
def consonant
'[^aeiou]'
end
def consonant_followed_by_qu
/^[^aeiou]*qu/
end
def vowel_sound
/^[aeiou]|^xr|^yt/
end
def consonant_cluster_y
/^[^aeiou]+y/
end
end
A huge amount can be learned from reading other people’s code. This is why we wanted to give exercism users the option of making their solutions public.
Here are some questions to help you reflect on this solution and learn the most from it.
Level up your programming skills with 3,118 exercises across 52 languages, and insightful discussion with our volunteer team of welcoming mentors. Exercism is 100% free forever.
Sign up Learn More
Community comments