2016-12-05 2 views
1

Мне нужно создать программу, в которой я должен попросить пользователя указать свое имя и фамилию на одной строке. Если пользователь ставит только свое первое имя ИЛИ, оно будет отклонено через исключение. Я продолжаю получать ошибку в конце (ниже).Ошибка инициализации Ruby Исключение

class MyNewException < Exception 
     attr_accessor :first, :last 
     def initialize (first, last) 
     @first = first 
     @last = last 
     end 
    end 

print "Enter your first and last name:" 

begin 

first, last = gets.chomp.split 

print "Hello," + first + " " + last + "!" 

if last.size == 0 
    raise MyNewException, "Sorry, I didn't catch that! Try again:" 
end 
rescue MyNewException 
    puts "Sorry, I didn't catch that. Try again:" 
    retry 
end 

получаю сообщение об ошибке:

testing.rb:15:in `+': no implicit conversion of nil into String (TypeError) 
+0

добавить значение по умолчанию определения функции инициализации (первый = ноль, последний = ноль) ' – Beginner

+0

Две ошибки здесь: одна из них - отсутствие запятой (' raise MyNewException ", извините, я не совсем понял это! Повторите попытку:" ') или явное построение исключения (' raise MyNewException.new ("Извините, Я не совсем понял это! Повторите попытку: ")'); другой - неправильный конструктор для вашего исключения. Почему у вашего исключения есть имя? :) Исключения обычно имеют только сообщение в своем конструкторе по умолчанию. Если вы действительно хотите создать пользовательское исключение с именем, вы должны поднять его с помощью 'raise MyNewException.new ('John', 'Doe')'. – Amadan

+0

@NewbeeDev Спасибо, что сработал! Кроме того, должен ли я создать цикл в рамках спасения, чтобы запросить у пользователя полное имя? –

ответ

1

raise() docs неисправны. Вы можете сделать это:

puts "Enter your first and last name:" 
name = gets.chomp 

class MyNewException < Exception 

    def initialize(str) 
    super(str) #pass the value for the message property to the parent class 
    end 

end 

begin 
    raise MyNewException, "Sorry, I didn't quite catch that! Try again:" 
rescue MyNewException => e 
    puts e.message 
end 

--output:-- 
Enter your first and last name: 
Sarah Kim 
Sorry, I didn't quite catch that! Try again: 

Или:

puts "Enter your first and last name:" 
name = gets.chomp 

class MyNewException < Exception 

    attr_accessor :first, :last 

    def initialize(user_name, exception_message) 
    @first, @last = user_name.split 
    super exception_message 
    end 

end 

begin 
    raise MyNewException.new(name, "I didn't quite catch that! Try again:") 
rescue MyNewException => e 
    puts e.message 
    puts e.first 
    puts e.last 
end 

--output:-- 
Enter your first and last name: 
Sarah Kim 
I didn't quite catch that! Try again: 
Sarah 
Kim 

Вот как написать бесконечный цикл, чтобы получить ввод данных пользователем:

class Person 
    attr_accessor :first, :last 

    def initialize(first, last) 
    @first = first.capitalize 
    @last = last.capitalize 
    end 
end 

while true 
    puts "Enter your first and last name:" 
    first, last = gets.chomp.split 
    #Show what you got: 
    p first 
    p last 

    if first and last 
    #If no names were entered, both first and last will be nil. 
    #If one name was entered, first will evaluate to true and last will be nil. 
    #If two names were entered, first and last will evaluate to true. 
    #If two or more names were entered, first and last will evaluate to true. 
    user = Person.new first, last 
    break #jump to the line immediately after the infinite loop 
    end 

    puts "Sorry, you must enter both a first and a last name. Try again" 
end 

puts "Thanks #{user.first} #{user.last}!" 
+0

Спасибо за два совета !!! Теперь я смущен, когда поместить цикл для повторного запроса, чтобы повторить попытку для нового ввода имени ... Я снова делаю класс выше для циклов? @ 7stud –

+0

Нет, класс должен идти в самый верх - вне цикла. Как правило, когда вы хотите спросить кого-либо о вводе, вы создаете бесконечный цикл, который продолжает запрашивать ввод много раз, затем вы выходите из цикла, если вход правильный, что не позволит снова задать вопрос. Для этого вам не нужно исключение. – 7stud

+0

Мне кажется, что вы пытаетесь смешивать объект Exception и объект Person. Непонятно, почему вы это делаете, то есть почему должен использоваться объект Exception для хранения ввода пользователя? – 7stud

1

Создать цикл, сделать ваш метод проб и ошибок. в качестве моего ответа я выбираю в то время как петля

i = 0 
while i < 1 do 

    if condition == true 
     # display your greetings then increment loop to end 
     i += 1 
    else 
     # display error message 
    end 

end 

Так что ваш код будет как этого

class MyNewException < Exception 

    attr_accessor :first, :last, :valid 

    def initialize(first, last) 
    @first = first 
    @last = last 
    @valid = true 
    if first.empty? || last.empty? then 
     @valid = false 
    end 
    end 

end 

i = 0 

while i < 1 do 

    print "Enter your first name: " 
    firstname = gets.chomp 
    print "Enter your last name: " 
    lastname = gets.chomp 

    name = MyNewException.new(firstname, lastname) 

    if name.valid then 
     puts "Greetings " << name.first << " " << name.last 
     i += 1 
    else 
     puts "I didn't quite catch that! Try again:" 
    end 

end 

enter image description here

+0

Кому, кто голосует, пожалуйста, объясните почему! – Beginner

+0

Не знаю, почему кто-то проголосовал за это LOL !!!! Ты совершенно потрясающий! Основная причина, по которой я борюсь, заключается в том, что вывод для этой программы должен быть первым и последним, указанным одновременно.Таким образом, пользователь должен иметь возможность ввести свое полное имя в начале в целом, а не «Введите свое имя, введите свою фамилию» –

+0

@SarahKim, возможно, отмечая его ответ и upvote, заставляет меня удовлетворять после моей напряженной работы в этом коде:) – Beginner

Смежные вопросы