eliza.lisp 1.4 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546
  1. (in-package :cl-user)
  2. (defpackage chatikbot.eliza
  3. (:use :cl
  4. :chatikbot.patmatch
  5. :chatikbot.utils)
  6. (:export :?is
  7. :?or
  8. :?and
  9. :?not
  10. :?*
  11. :?+
  12. :??
  13. :?if
  14. :eliza
  15. :read-from-string-no-punct))
  16. (in-package :chatikbot.eliza)
  17. (defun punctuation-p (char)
  18. (find char ".,;:'!?#-()\\\""))
  19. (defun read-from-string-no-punct (input)
  20. "Read from an input string, ignoring punctuation."
  21. (read-from-string
  22. (concatenate 'string "(" (substitute-if #\space #'punctuation-p input) ")")))
  23. (defun switch-viewpoint (words)
  24. "Change I to you and vice versa, and so on."
  25. (sublis '((I . you) (you . I) (me . you) (am . are)
  26. (я ты) (ты я) (меня тебя) (тебя меня))
  27. words))
  28. (defun use-eliza-rules (input rules)
  29. "Find some rule with which to transform the input."
  30. (rule-based-translator input rules
  31. :action #'(lambda (bindings responses)
  32. (sublis (switch-viewpoint bindings)
  33. (random-elt responses)))))
  34. (defun eliza (input rules)
  35. (let ((r (use-eliza-rules input rules)))
  36. (cond
  37. ((null r) nil)
  38. ((and (consp (car r)) (eq 'function (caar r)))
  39. (apply (cadar r) (cdr r)))
  40. ((keywordp (car r)) r)
  41. (t (print-with-spaces (flatten r))))))