Ruby if statements 3 conditions - ruby

puts 'guess my favorite num'
x = gets.chomp
unless x.kind_of?(Fixnum)
puts "it's not a Numeric symbol"
if x=="2"
puts "Well done!"
if x!=2 || x.is_a?(Fixnum)
puts "Try more, dude"
end
end
end
Trying to learn ruby, but my code is not work :-( Need 3 DIFFERENT conditions for var. Where is a bug ?

Consider this:
#!/usr/bin/env ruby
puts "Guess my favorite num."
x = gets.chomp
begin
if Integer(x) == 2
puts "Well done!"
else
puts "Try more, dude."
end
rescue ArgumentError
puts "It's not an integer."
end

Semi-contrived example, but you're probably looking for elsif:
puts 'enter a favorite num'
x = gets.chomp.to_i
if x == 2
puts "you entered 2"
elsif x !=2
puts "you did not enter 2"
end
Also--as #Jan Dvorak points out--the gets method returns a string, which you would want to convert (to integer in this case).
Another solution would be to use a case statement:
print 'enter a favorite num'
x = gets.chomp.to_i
case x
when 2
puts "you entered 2"
else
puts "you did not enter 2"
end

You did probably mean something like that:
loop do
puts 'guess my favorite num'
x = gets.chomp
case x
when /\D/
puts "it's not a Numeric symbol"
when "2"
puts "Well done!"
break
else
puts "Try more, dude"
end
end

Related

How to sum variables values RUBY

First, I am new to ruby so please be gentle hehe.
I have a school project where the assignment is to calculate the total cost of a project. In my code, the user is giving the variables some input. Later on, I want to show the total of all these inputs. (the inputs is number)
So basically I need to add them up and it needs to give me a sum of them.
How do I do that?
Hope you amazing people can help me:)
Here is my code:
file = File.new("testing.txt", "a")
class Project
def call_acc
prompt = "> "
puts
puts "What is the salary for an accountant?"
print prompt
while #accountant = gets.chomp
if !/\A\d+\z/.match(#accountant)
puts
puts "Error: Only use numbers, please try again"
print prompt
else
break
end
end
end
def call_dev
prompt = "> "
puts
puts "What is the salary for an developer?"
print prompt
while #developer = gets.chomp
if !/\A\d+\z/.match(#developer)
puts
puts "Error: Only use numbers, please try again"
print prompt
else
break
end
end
end
def call_mana
prompt = "> "
puts
puts "What is the salary for the top management?"
print prompt
while #management = gets.chomp
if !/\A\d+\z/.match(#management)
puts
puts "Error: Only use numbers, please try again"
print prompt
else
break
end
end
end
def call_office
prompt = "> "
puts
puts "What is the total office rent for the project?"
print prompt
while #office = gets.chomp
if !/\A\d+\z/.match(#office)
puts
puts "Error: Only use numbers, please try again"
print prompt
else
break
end
end
end
def call_lunch
prompt = "> "
puts
puts "What is the daily cost for lunch per person?"
print prompt
while #lunch = gets.chomp
if !/\A\d+\z/.match(#lunch)
puts
puts "Error: Only use numbers, please try again"
print prompt
else
break
end
end
end
def call_utilites
prompt = "> "
puts
puts "What is the total cost for utilites (internet, subscriptions etc)?"
print prompt
while #utilites = gets.chomp
if !/\A\d+\z/.match(#utilites)
puts
puts "Error: Only use numbers, please try again"
print prompt
else
break
end
end
end
def call_show
prompt = "> "
puts "____________________________________"
puts
puts "Is this information correct?"
puts
puts "Accountant salary (per hour): #{#accountant}kr\nDevelepor salary (per hour): #{#developer}kr\nTop management salary (per hour): #{#management}kr"
puts
puts "Total rent cost of office space: #{#office}kr\nLunch per person per day: #{#lunch}kr\nTotal cost of utilites #{#utilites}kr"
puts
puts "____________________________________"
puts "Yes or No"
print prompt
while user_imput = gets.chomp.upcase
case user_imput
when "YES"
file = File.new("testing.txt", "a")
file.puts("Account salary: #{#accountant}kr\nDeveloper selary: #{#developer}kr\nTop management salary #{#management}kr\nTotal rent cost: #{#office}kr\nLunch per person #{#lunch}kr\nUtilites cost #{#utilites}kr")
file.close
puts
puts "The information has now been stored"
puts "____________________________________"
break
when "NO"
puts
puts "The information has not been stored. Exiting application"
puts "____________________________________"
abort
else
puts
puts "Please either write Yes or No"
print prompt
end
end
end
def call_total
prompt = "> "
puts
puts "________Your information_______"
puts
puts "Accountant salary (per hour): #{#accountant}kr\nDevelepor salary (per hour): #{#developer}kr\nTop management salary (per hour): #{#management}kr"
puts
puts "Total rent cost of office space: #{#office}kr\nLunch per person per day: #{#lunch}kr\nTotal cost of utilites #{#utilites}kr"
puts
puts "________Total cost of project________"
puts
puts ?????????#accountant + #developer??????????????+
puts
end
project = Project.new
require 'io/console'
select = 0
prompt = "> "
puts
puts
puts "Welcome to KEA"
puts "____________________________________"
loop do(select != 7)
puts
puts "Press 1 to calculate"
puts "____________________________________"
select = STDIN.getch.to_i
if (select == 1)
project.call_acc
project.call_dev
project.call_mana
project.call_office
project.call_lunch
project.call_utilites
project.call_show
project.call_total
break
else
puts
puts "Invalid input. Please try again"
puts "____________________________________"
end
end
end
Answering the question stated in title:
numbers =
loop.inject([]) do |acc, _|
val = gets.to_i
break acc unless val > 0
acc << val
end
numbers.reduce(:+)

Handling Ruby Case Statement

I tried to rewrite the "if/else statement" in the following piece of code by replacing it with a "case" statement, and I am deadly stuck with it for a few hours - what am I missing?
puts "Welcome to 'Guess My Number!'"
print "What is your name?"
input = gets
name = input.chomp
puts "Welcome, #{name.upcase!}!"
puts "I've got a random number between 1 and 100!"
puts "Can you guess it?"
target = rand(100) + 1
num_guesses = 0
guessed_it = false
until num_guesses == 10 || guessed_it
remaining_guesses = 10 - num_guesses
puts "You've got #{remaining_guesses.to_s} guesses left!"
print "Make a guess, put down a number: "
guess = gets.chomp.to_i
num_guesses = num_guesses + 1
end
puts case verification
when guess < target
then "Ooops. Your guess was LOW."
when guess > target
then "Ooops. Your guess was HIGH."
when guess < -1
then puts "Oooops. You have entered a number lower that 1!"
when guess > 100
then puts "Oooops. You have entered a number higher than 100!"
when guess =~ /^([w])/
then puts "Ooops. Looks like you have entered a non numeric
value!"
when guess == String
then puts "Oooops! Looks like you have entered a non numeric
value"
when guess == target
then puts "Good job, #{name}!"
puts "You guessed my number in #{num_guesses} guesses!"
guessed_it = true
end
unless guessed_it
puts "Sorry, you didn't get my number. My number was #{target}."
end
The "case statement" was used to replace and enhance the logic of the following if else statement:
if guess < target
puts "Ooops. Your guess was LOW."
elsif guess > target
puts "Ooops. Your guess was HIGH."
elsif guess == target
puts "Good job, #{name}!"
puts "You guessed my number in #{num_guesses} guesses!"
guessed_it = true
end
Your problem is that you're using the form of case with the optional condition, but you're using when clauses as if you were using the condition-less case.
puts case
when guess < target
"Ooops. Your guess was LOW."
should work.
Further explanation:
using case without a condition, the earliest when branch with a truthy expression is executed. This is what you want here.
But you were using case with verification. In this case, all branches are compared to verification, and the first branch where verification === branch condition is true is executed.
Since in your example I'm guessing verification is always nil, and all your branches' conditions are always true or false, no branch will ever get executed.
You can use a case statement like so:
class String
def green;"\e[32m#{self}\e[0m";end
def yellow;"\e[33m#{self}\e[0m";end
def cyan;"\e[36m#{self}\e[0m";end
def bg_blue;"\e[44m#{self}\e[0m";end
def bold;"\e[1m#{self}\e[22m";end
def underline;"\e[4m#{self}\e[24m";end
def border(num);"\n#{'-' * num}\n#{self}\n#{'-' * num}\n";end
end
puts;puts "Welcome to 'Guess My Number!'".bold.bg_blue;puts
print 'What is your name? '.green
name = gets.chomp
puts "\nWelcome, #{name.upcase!}!\n".cyan.underline
puts "I've got a random number between 1 and 100!\nCan you guess it?".border(44)
target = rand(100) + 1
num_guesses = 0
guessed_it = false
until num_guesses == 10 || guessed_it
remaining_guesses = 10 - num_guesses
puts "\nYou've got #{remaining_guesses} guesses left!\n"
puts;print 'Make a guess, put down a number: '
guess = gets.chomp
case guess.to_i
when (1...target)
puts 'Ooops. Your guess was LOW'.yellow.border(26)
when (target + 1..100)
puts 'Ooops. Your guess was HIGH'.yellow.border(26)
when target
puts; puts; puts
puts "Good job, #{name}!".bold.green
puts 'You guessed my number in ' + "#{num_guesses} guesses!".cyan
puts; puts; puts
guessed_it = true
else
puts "Oooops. You didn't enter a number from 1 to 100".yellow.border(47); puts
end
num_guesses += 1
end
unless guessed_it
puts;puts;puts "Sorry, you didn't get my number. My number was #{target}.".yellow;puts
end
Thanks a lot to everybody! With your invaluable help I managed to regain patience in my soul and satisfaction from this small task :) My mistake is that I violated the rules of common sense by trying to run several pieces of code in a wrong sequence. I moved the case statement inside the until loop and now all I have to do is correct the mistakes in particular when/then statements. It works :)
until num_guesses == 10 || guessed_it
remaining_guesses = 10 - num_guesses
puts "You've got #{remaining_guesses.to_s} guesses left!"
print "Make a guess, put down a number: "
guess = gets.chomp.to_i
num_guesses = num_guesses + 1
puts case
when guess < target
then "Ooops. Your guess was LOW."
when guess > target
then "Ooops. Your guess was HIGH."
when guess < -1
then puts "Oooops. You have entered a number lower that 1!"
when guess > 100
then puts "Oooops. You have entered a number higher than 100!"
when guess =~ /^([w])/
then puts "Ooops. Looks like you have entered a non numeric value!"
when guess == String
then puts "Oooops! Looks like you have entered a non numeric value"
when guess == target
then puts "Good job, #{name}!"
puts "You guessed my number in #{num_guesses} guesses!"
guessed_it = true
end
end
unless guessed_it
puts "Sorry, you didn't get my number. My number was #{target}."
end

Ruby exact string match

so I'm teaching myself Ruby, and I made a simple heads or tails game. The user types in 'h' to choose heads and 't' to select tails. Under normal use, everything works fine, but unfortunately if the user types in 'th' they can win every time. How do I only reward exact string matches?
puts "~~~~~ HEADS OR TAILS ~~~~~"
print "Choose: Heads or Tails? (h,t): "
choice = gets.to_s
flip = rand(0..1)
if !choice.match('h') && !choice.match('t')
puts "oops"
elsif flip === 0
puts "The coin flipped as heads!"
puts "You chose: " + choice.to_s
if choice.match('h')
puts "YOU WIN!"
elsif !choice.match('h')
puts "YOU LOSE."
end
elsif flip === 1
puts "The coin flipped as tails"
puts "You chose: " + choice.to_s
if choice.match('t')
puts "YOU WIN!"
elsif !choice.match('t')
puts "YOU LOSE."
end
end
choice.match('t') will be truthy for any string where there is t anywhere in it. Use choice == 't'. Or, if you really want to be using regular expressions, choice.match(/\At\Z/) (match beginning, t and end of the string).
To fix your issue, you can update your code with below changes:
1. Replace match with eql? in the above code. This will perform
case-sensitive string comparisons in the program. In order to
ensure, for case-insensitive comparisons, you can use 'casecmp'
method defined in ruby.
2. Also, you can enhance your code by replacing
to_s with chomp() method it will strip off \r,\n.
Updated code is as follows:
puts "~~~~~ HEADS OR TAILS ~~~~~"
print "Choose: Heads or Tails? (h,t): "
choice = gets.chomp
flip = rand(0..1)
if !choice.eql?('h') && !choice.eql?('t')
puts "oops"
elsif flip === 0
puts "The coin flipped as heads!"
puts "You chose: " + choice
if choice.match('h')
puts "YOU WIN!"
elsif !choice.match('h')
puts "YOU LOSE."
end
elsif flip === 1
puts "The coin flipped as tails"
puts "You chose: " + choice
if choice.match('t')
puts "YOU WIN!"
elsif !choice.match('t')
puts "YOU LOSE."
end
Also, you can refer to the document "http://ruby-doc.org/core-2.2.2/Object.html#method-i-eql-3F".

Ending while loops in one method from another method in Ruby?

I'm working on a simple text-based dungeon game in Ruby, and I've run into a snag. Basically, I have one room with a locked door. The key is found in another room and I want the door to be unlocked once the key has been found.
Here's what I've got so far:
def chest_room
puts "You are in a small, round room."
puts "On the floor in front of you is a small wooden chest."
puts "It does not appear to be locked."
puts "What do you do?"
chest_open = false
while true
prompt; next_move = gets.chomp
if next_move == "open chest"
chest_open = true
puts "Inside the chest, you see a small, brass key."
puts "What do you do?"
prompt; next_move = gets.chomp
elsif next_move == "take key" and chest_open
key_present = true
puts "You take the key and slip it into a pocket."
puts "What do you do?"
prompt; next_move = gets.chomp
elsif next_move == "go back"
start()
else puts "I don't understand you."
puts "What do you do?"
prompt; next_move = gets.chomp
end
end
end
def start
puts "You find yourself in a dank room lit by torches."
puts "There are three doors leading out of here."
puts "What do you do?"
door_open = false
key_present = false
while true
prompt; next_move = gets.chomp
if next_move == "door 1"
chest_room()
elsif next_move == "door 2"
dais()
elsif next_move == "door 3" and not door_open
puts "This door is securely locked."
puts "You'll need to find some way of opening it before you can enter."
puts "What do you do?"
prompt; next_move = gets.chomp
elsif next_move == "door 3" and key_present
door_open = true
puts "The key you found fits easily into the lock."
puts "With a click, you unlock the door!"
orb_room()
else
puts "I don't understand you."
puts "What do you do?"
prompt; next_move = gets.chomp
end
end
end
Any input or advice? Essentially, I want to end the door_open = false loop once the key is found, but I can't figure out how to set door_open = true in the chest_room method then call it from the start method. Thanks!
What you really need is to back up and think out the design again. You have a Room, and it has a property "open" or "closed". You have a Key, and you need the key to change the state of that open/closed property.
Write out what you want to do, and think about how to model it as a Room and a Key, and you'll be on a better track.
(No, I don't want to give you the answer. Figuring it out is more important.)
You're having scope issues. make the door_open or key_present instance variables by putting an # in front of them. Then any method can access them. also case/when is cleaner than if elsif
while !#key_present # #key_present can be modified in another method
prompt; next_move = gets.chomp
case
when "door 1" == next_move then chest_room() # put constants first when comparing ==
when "door 2" == next_move then dais()
# more conditions
end
end

Code never enter any of the if statements

begin
selected_option = gets.chomp
if selected_option == 1
puts "Welcome to the Welcome Screen!"
elsif selected_option == 2
puts "This is the options menu."
elsif selected_option == 3
puts "Logging out. Goodbye!"
else
puts "Please select a valid option."
end
end while not selected_option == 3
I enter in 1 or 2 or 3 and I always get the "Please enter a valid option" message. I'm guessing that's because the chomp method retrieves the input as a string.
Any way around this sans using quotes around the options?
gets.chomp.to_i
Will convert it to an integer.
You may also want to use a switch instead:
begin
selected_option = gets.chomp.to_i
case selected_option
when 1
puts "Welcome to the Welcome Screen!"
when 2
puts "This is the options menu."
when 3
puts "Logging out. Goodbye!"
else
puts "Please select a valid option."
end
end while not selected_option == 3

Resources