2010-10-27 1 views
2

Когда я выполняю следующую программу Common Lisp, вызвав (play), я получаю ошибку: Argument X is not a NUMBER: GuessЦелое значение не является числом в общем Lisp?

;;;; number-game.lisp 
;;;; 
;;;; Andrew Levenson 
;;;; 10/25/2010 
;;;; 
;;;; Simple number guessing game. User has 
;;;; five guesses to determine a number between 
;;;; one and one hundred, inclusive (1-100). 

;;; Set global variable for the target number: 
(defparameter *target* nil) 

;;; Set the iterator so we may check the number of guesses 
(defparameter *number-of-guesses* 0) 

;;; Welcome the user 
(defun welcome-user() 
    (format t "Welcome to the number guessing game!~%")) 

;;; Prompt for a guess 
(defun prompt-for-guess() 
    (format t "Please enter your guess (1-100): ") 
    (finish-output nil) ; nil directs finish-output to standard IO 
    (check-guess 'read-guess)) 

;;; Read in a guess 
(defun read-guess() 
    (let ((guess (parse-integer(read-line *query-io*)))) 
     (if (numberp guess) ; If true, return guess. Else, call prompt-for-guess 
      (progn 
       (setq *number-of-guesses* (+ *number-of-guesses* 1)) 
       'guess) 
      (prompt-for-guess)))) 

;;; Check if the guess is higher than, lower than, or equal to, the target 
(defun check-guess (fn) 
    (let ((guess (funcall fn))) 
     (if (= guess *target*) 
      (equal-to) 
      (if (> guess *target*) 
       (greater-than (guess)) 
       (if (< guess *target*) 
        (less-than (guess))))))) 

;;; If the guess is equal to the target, the game is over 
(defun equal-to() 
    (format t "Congratulations! You have guessed the target number, ~a!~%" *target*) 
    (y-or-n-p "Play again? [y/n] ")) 

;;; If the guess is greater than the target, inform the player. 
(defun greater-than (guess) 
    (format t "Sorry, ~a is greater than the target.~%" guess) 
    (if (< *number-of-guesses* 6) 
     (prompt-for-guess) 
     (game-over))) 

;;; If the guess is less than the target, inform the player. 
(defun less-than (guess) 
    (format t "Sorry, ~a is less than the target.~%" guess) 
    (if (< *number-of-guesses* 6) 
     (prompt-for-guess) 
     (game-over))) 

;;; If the player has run out of guesses, give them the option 
;;; of playing the game again. 
(defun game-over() 
    (y-or-n-p "You have run out of guesses. Play again? [y/n] ")) 


;;; Play the game 
(defun play() 
    ;; If it's their first time playing this session, 
    ;; make sure to greet the user. 
    (unless (> *number-of-guesses* 0) 
     (welcome-user)) 
    ;; Reset their remaining guesses 
    (setq *number-of-guesses* 0) 
    ;; Set the target value 
    (setq *target* 
     ;; Random can return float values, 
     ;; so we must round the result to get 
     ;; an integer value. 
     (round 
      ;; Add one to the result, because 
      ;; (random 100) yields a number between 
      ;; 0 and 99, whereas we want a number 
      ;; from 1 to 100 inclusive. 
      (+ (random 100) 1))) 
    (if (equal (prompt-for-guess) "y") 
     (play) 
     (quit))) 

Что я делаю неправильно, что guess не числовое значение в check-guess?

+1

Чтобы сэкономить время: в какой строке вы получаете эту ошибку? –

+1

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

+0

@ ring0 Извините, но я не знаю, как получить номера строк из ошибок REPL. :/ – Andy

ответ

9

Функция read-guess возвращает символ GUESS, используя 'guess, а не значение guess (т.е. без единой цены).

У меня также есть другие проблемы, например (greater-than (guess)) оценивает угадывание как функцию. Вам также придется исправить это.

+0

Да, я тоже это заметил. – Gabe

+0

Как передать 'guess' как переменный аргумент для функций? – Andy

+0

Используйте '' guess' вместо '(guess)'. –

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