2015-05-17 2 views
1

Я создаю текстовую игру на питоне и попал в дорожный блок. У меня есть функция, которая проверяет, содержит ли пользовательский ввод определенные слова, и если он это делает, возвращает пользовательский ввод, иначе он будет запрашивать ввод. Если вы напишете что-то, не содержащее одно из слов, оно снова вызовет функцию.Рекурсивная функция с теми же аргументами

def contains_words(prompt, words): 

    user_input = raw_input(prompt).strip().lower() 


    if user_input == "instructions": 
     print 
     instructions() 
     print 
     contains_words(prompt, words) 

    elif user_input == "i" or user_input == "inventory": 
     if len(inventory) == 0: 
      print 
      print "There is nothing in your inventory." 
      print 
      contains_words(prompt, words) 
     else: 
      print "Your inventory contains: " + inventory 
      contains_words(prompt, words) 

    else: 
     if user_input in words: 
      return user_input 
     else: 
      print 
      print "I did not understand your answer, consider rephrasing." 
      contains_words(prompt , words) 

Вот я зову его:

pizza = contains_words("Do you like pizza?", ["yes", "no"]) 

В этой функции вы можете вызвать инструкции или инвентарь, а затем она будет вспомнить функцию. Все работает нормально, если вы вставляете одно из слов в свой ответ при первом запросе. Проблема возникает, когда вы вводите что-то неправильное, воспитываете инвентарь или воспитываете инструкции. Это заставляет функцию ничего не возвращать, а не вводить пользователя. Почему это происходит? Это потому, что функция сбрасывается, поэтому параметр равен none?

+0

(a) Вы можете исправить отступы? Используйте ctrl + k с вашим кодовым блоком для этого (b) почему вы вызываете метод 'contains_words' и без' self' в разных местах? –

+4

Все ваши рекурсивные вызовы должны возвращать их результаты. 'return contains_words (подсказка, слова)' – Ryan

+0

«Self» - это случайность. Удаление – conyare

ответ

1

Давайте рассмотрим образец вызова этой функции.

pizza = contains_words("Do you like pizza?", ["yes", "no"]) 

Произнести пользовательские входы instructions. Ваш первый оператор if равен True, поэтому мы входим в этот блок, вызывается instructions() (предположительно печатая инструкции на консоль), а contains_words вызывается снова. Предположим, что на этот раз пользователь вводит yes. Мы перейдем к последнему сообщению if, это будет True, и этот звонок contains_words вернет yes - туда, где он был вызван.

Итак, теперь мы восстанавливаем стек до первоначального вызова contains_words. Возвращаемое значение игнорируется, потому что функция вызывается в строке сама по себе, а не как аргумент другой функции или оператора. Теперь мы закончили с этим блоком if, и следующая вещь в функции ... ничего. Остальная часть if s. elif s и else s ничего не значит (как оригинал if оценивается до True), и мы выходим из нижней части функции. Он ничего не возвращает (фактически None). (Проверьте тип pizza увидеть.)

Решение либо изменить рекурсивные вызовы на return contains_words(prompt, words) так, когда функция выпадает из каждого рекурсивного вызова он передает возвращаемое значение из стека, или, так как это просто хвост рекурсии в любом случае, заменить его с петлей:

def contains_words(prompt, words): 

    while True: 
     user_input = raw_input(prompt).strip().lower() 


     if user_input == "instructions": 
      print 
      instructions() 
      print 


     elif user_input == "i" or user_input == "inventory": 
      if len(inventory) == 0: 
       print 
       print "There is nothing in your inventory." 
       print 
      else: 
       print "Your inventory contains: " + inventory 

     else: 
      if user_input in words: 
       return user_input 
      else: 
       print 
       print "I did not understand your answer, consider rephrasing." 

, что позволит избежать проблем с памятью, связанные с потенциально много рекурсии.

+0

Ну ладно, спасибо за объяснение. – conyare

1

Вам нужно всего лишь заменить операторы кода contains_words(prompt, words) по return contains_words(prompt, words)

+0

Какова причина этого? – conyare

1

Когда вы рекурсию, вам нужно вернуть результат.

return contains_words(prompt , words) 
+0

Какова причина этого? – conyare

+0

Если вы ничего не возвращаете, функция возвращает 'None' неявно, но вы сказали, что должны возвращать пользовательский ввод. – recursive

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