Joshua Blewitt

Coding Challenges in: Ruby

I'm currently learning Ruby at the moment and I thought I'd challenge myself by doing several coding problems and document them here.

All the code mentioned in this post can be found on my GitLab here.

So, let's kick things off with a famous one.

FizzBuzz

Ahh yes, FizzBuzz! Known to be used in tech interviews around the world. Here's what the challenge involves:

  • Write a program that prints 1 to 100
  • For numbers divisible by 3, print "Fizz"
  • For numbers divisible by 5, print "Buzz"
  • For number divisible by 3 and 5, print "FizzBuzz"

Sounds simple right? I'll break things down for each step. Let's get to it!

So, printing 1 to 100 is going to require a loop of some kind.

counter = 1

while counter <= 100
    puts counter
    counter+=1
end

As you can see, this while loop will continue to print the variable 'counter' until it is no longer less than or equal to 100! In the loop, after printing the variable to the screen, the value is incremented by 1.

Okay, that's done - next it needs to print "Fizz" if it is divisible by 3, "Buzz" if it is divisible by 5 or "FizzBuzz" if it is divisible by 3 and 5.

counter = 1

while counter <= 100
    if counter % 3 == 0 && counter % 5 == 0
        puts "FizzBuzz"
    elsif counter % 3 == 0
        puts "Fizz"
    elsif counter % 5 == 0
        puts "Buzz"
    else
        puts counter
    end
    counter+=1
end

And if we run the program, we will see this!

1
2       
Fizz    
4       
Buzz    
Fizz    
7       
8       
Fizz    
Buzz    
11      
Fizz    
13      
14      
FizzBuzz

Looks good! 6 is divisible by 3 so that prints Fizz, 10 is divisible by 5 so that prints Buzz and 15 is divisible by both so it prints FizzBuzz!

However... what if I did this?

while counter <= 100
    if counter % 3 == 0
        puts "Fizz"
    elsif counter % 5 == 0
        puts "Buzz"
    elsif counter % 3 == 0 && counter % 5 == 0
        puts "FizzBuzz"
    else
        puts counter
    end
    counter+=1
end

That will result in....

1
2
Fizz
4
Buzz
Fizz
7
8
Fizz
Buzz
11
Fizz
13
14
Fizz

Whoah! That doesn't look right! Why?

It all lies in the order of where the if statements are placed. In the example above, we can see that the first if statement checks if it is divisible by 3, if it is - it prints Fizz, if not, it will check if it is divisible by 5.

Which means that in every scenario it will never hit that final elsif statement! So if we move that statement to the front, it will always check each number if it is divisible by 3 and 5. Then, check if it is divisible by 3 or 5 individually.

Problem solved! ✔

Chessboard

The summary of the problem is:

Write a program that creates a string that represents an 8×8 grid, using newline characters to separate lines. At each position of the grid there is either a space or a "#" character. The characters should form a chessboard.

In fact, this problem came from the Eloquent Javascript book! (Which is excellent by the way)

Let's get to it!

Would you believe it that I struggled with this one?

I get lost in the various different states of loops.

Seriously, I started off with this (in an attempt to draw something to the console.):

#define the size of the board
size = 4
#blank string - this is intentional
board = ""

#x axis
x = 0

#y axis
y = 0

#variable to determine when to add a new line
counter = 0

while x <= size
    board += "# "
    x += 1
    if counter > 1 && counter <= 4
        board += "\n"
        board += "# "
        x -= 1
        if y <= 4
            board += "# "
            y += 1
        end
    end
    counter += 1
end

puts board

And the output was this:

# # #
# # #
# # #
# # # # #

Not only is the code messy and unreadable in places but it also doesn't print a square!

So, I took this back to basics of Ruby - if I'm doing something too complex, then I'm doing it wrong.

And in which, I came up with this:

#define the size of the board
size = 8
#blank string - this is intentional
board = ""

#x axis
x = 0

#y axis
y = 0

#variable to determine when to add a new line
counter = 0

while x <= size
    8.times {board += "# "}
    x += 1
    if y <= size
        board += "\n"
    end
    y += 1
end

puts board

Which in turn prints...

# # # # # # # #
# # # # # # # #
# # # # # # # #
# # # # # # # #
# # # # # # # #
# # # # # # # #
# # # # # # # #
# # # # # # # #
# # # # # # # #

Hooray! An 8 x 8 Chessboard!

Problem solved! ✔

Finding Duplicates

Finally, we have a problem from the website Ruby Guides.

The problem is...

Given an array with Integer values you need to find all the duplicated numbers.

This is another one that I struggled with - but it got me to think on my feet and research dfferent ways on how to solve the problem.

Let's get to it!

So, we need an array with duplicate integer values for us to find duplicate numbers.

#array defined with duplicate numbers
numbers1 = [1,2,2,2,3,3,4,5]

But after that, how do I write a method that finds duplicated elements? Maybe a for each statement?

I was eventually getting frustrated so I turned to the internet (or more specifically Stack Overflow). Eventually I found about the use of the built in method called find-all.

So this returns an array containing all elements of enumerable for which the given block (the code inbetween curly brackets) returns a true value. If there isn't a block, an enummerator is returned instead.

With this in mind, I did some more research and found a way to use the code block in find-all to return duplicates. My research lead me to count. Which is used to return a number of items through enumeration.

So if we can return an array with all the elements and then return a number of items, we can use that to find duplicates in an array!

I decided to write a method which has an if statement to determine if the array has any duplicates to begin with.

To achieve this, I used uniq. Like so:

if array.uniq.length == array.length
        puts "No duplicates!"
    else
        puts "There are duplicates"

So putting this all together, I wrote this to solve the problem:

#method called find duplicates, takes in array as an argument
def find_duplicates (array)
    #if the array length with unique values is equal to all elements in the array
    if array.uniq.length == array.length
        puts "No duplicates!"
    else
        puts "There are duplicates"
        #using the find_all method to return all elements from Enumerable.
        #then between the curly brackets, we check each element (e) in the array if there is a duplicate element in the array.
        array.find_all { |e| array.count(e) > 1 }
    end
end

#array defined with duplicate numbers
numbers1 = [1,2,2,2,3,3,4,5]

puts find_duplicates(numbers1)

Which gives the output of...

There are duplicates
2
2
2
3
3

As we can see, it prints the duplicates to the console!

Problem solved! ✔

Lessons learned

I've learnt a lot by doing these exercises: - Take the opportunity to do challenges, it expands your knowledge and problem solving skills. - Take your time, no rush. It doesn't hurt to take a break and do something else if you are struggling. - Don't beat yourself up if you get it wrong!

I hope you've enjoyed reading this post, expect more Ruby soon!

Thanks for reading!

Tags:


A photo of me!

I'm Joshua Blewitt, I'm passionate about product, a technology advocate, customer champion, curious mind and writer. I've worked for companies such as Rightmove, Domino's Pizza and IQVIA.

Let me know your thoughts!
More about me