2012-02-03 3 views
0

После того, как я задал вопрос с бабушкой, я хотел взять их совет и дополнить счетчик как класс. Deaf GrandmaОшибка классов в Ruby - NoMethod

Это где я в

puts 'Say something nice to Grandma.' 
puts 'You may need to shout > ' 

class Counter 
    counter = 0 
    def Plus 
    counter += 1 
    end 
    def Minus 
    counter -= 1 
    end 
    def Reset 
    counter = 0 
    end 
end 

MyCounter = Counter.new 

def speaks() 
    $speak = gets.strip 
    if $speak != 'Bye' 
     talk() 
    else 
     exitPlan() 
    end 
end 

def talk() 
    if $speak == $speak.downcase 
     puts 'Huh Speak up Sonny' 
    else 
     year = rand(1930..1951) 
     puts 'No not Since ' + year.to_s 
    end 
     MyCounter.Minus 
     if counter < 0 
      Counter.reset 
     end 
     puts 'Say something nice to Grandma' 
     speaks() 
end 

def exitPlan() 
    MyCounter.Plus 
    unless counter == 3 
     puts 'Say something nice to Grandma' 
     speaks() 
    else 
     puts 'good night Sonny' 
    end 
end 
speaks() 

Это NoMethod Ошибка

C:\Users\renshaw family\Documents\Ruby>ruby gran2.rb 
Say something nice to Grandma. 
You may need to shout > 
Hi 
No not Since 1939 
gran2.rb:10:in `Minus': undefined method `-' for nil:NilClass (NoMethodError) 
     from gran2.rb:35:in `talk' 
     from gran2.rb:22:in `speaks' 
     from gran2.rb:52:in `<main>' 

ответ

3

Когда вы делаете следующее:

class Counter 
    counter = 0 
end 

counter является локальной переменной и исчезает , когда вы выходите из определения класса, это означает, что он не существует в любое время позже, и, следовательно, counter - nil, и вы пытаетесь позвонить по нему - (nil) при выполнении counter -= 1, что приводит к NoMethodError. То, что вы, кажется, пытаются сделать, это инициализировать instance variable при конкретизации:

class Counter 
    def initialize 
    @counter = 0 
    end 

    def plus 
    @counter += 1 
    end 

    def minus 
    @counter -= 1 
    end 

    def reset 
    @counter = 0 
    end 
end 

Метод initialize это имя для конструктора в Ruby, и вызывается при вызове Counter.new. Также обратите внимание, что я изменил имена методов, чтобы начать с буквы в нижнем регистре, как это принято: имена классов капитализируются, методы и переменные являются строчными.

Я также хотел бы высоко препятствовать использованию глобальных переменных (например, $speak).

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