CLIPS сестра, предшественник и возрастные правила - PullRequest
0 голосов
/ 21 апреля 2020

У меня следующая проблема программирования CLIPS: Новая база знаний о семейных отношениях. Пожалуйста, примените следующую спецификацию:

  • используйте deftemplate для определения лица

  • атрибуты человека: имя, возраст, пол, дети,

  • каждый атрибут должен быть определен как слот, кроме дочерних, которые являются мультислотами

  • в половых слотах (разрешенные символы - женский мужчина)

  • добавить тип данных в каждый слот

  • использовать де-факто для добавления людей из диаграммы

  • определить правила:

- мать,

- отец,

- сестра,

- предшественник

- старый - дает разницу в возрасте между предшественником и потомством

Вот код, который я сделал:

(deftemplate person
    (slot name (type SYMBOL))
    (slot age (type INTEGER))
    (slot sex (type SYMBOL) (allowed-symbols female male))
    (multislot children (type SYMBOL))
)

(deffacts init
    (person (name Fernando) (age 55) (sex male) (children Jesus Celia))
    (person (name Maria) (age 50) (sex female) (children Jesus Celia))
    (person (name Jesus) (age 25) (sex male))
    (person (name Celia) (age 20) (sex female))
    (person (name Antonio) (age 70) (sex male) (children Fernando Ana))
    (person (name Ana) (age 38) (sex female))
    (person (name Calra) (age 68) (sex female) (children Fernando Ana))
)


(defrule mother
    (person (name ?name) (sex female) (children $?before ?child $?after))


=>
    (assert (mother ?name ?child))
    (printout t ?name " is mother of " $?child crlf))

(defrule father
    (person (name ?name) (sex male) (children $?before ?child $?after))


=>
    (assert (father ?name ?child))
    (printout t ?name " is father of " $?child crlf))


(defrule sister
    (children ?z ?x)
    (children ?z ?y)
    (female ?x)
    (not (test (eq ?x ?y)))
=>
    (assert sister ?x ?y))
    (printout t ?x "is a sister to " ?y crlf))

(defrule predecessor
(or
    (children ?x ?y)
    (and (children ?x ?z)(predecessor ?z ?y))
)
=>
(assert (predecessor ?x ?y)
(printout t ?x "is a predecessor to " ?y crlf))

(defrule old
    ?fact_no <- (person (name ?n) (age ?a1 ?a2))
    (test (<= ?a1 ?a2))

=>
    (assert (result (- ?a1 ?a2)))
    (printout t "There are " ?result " years" crlf))

Отношения матери и отца работают, но не остальные. Это дает мне следующие ОШИБКИ:

CLIPS> Loading Selection...

[CSTRCPSR4] Cannot redefine deftemplate person while it is in use.

ERROR:
(deftemplate MAIN::person

[CSTRCPSR1] WARNING: Redefining deffacts: init

[CSTRCPSR1] WARNING: Redefining defrule: mother +j+j
Defining defrule: father +j+j

[CSTRCPSR1] WARNING: Redefining defrule: sister 
[PRNTUTIL2] Syntax Error:  Check appropriate syntax for RHS patterns.

ERROR:
(defrule MAIN::sister
   (children ?z ?x)
   (children ?z ?y)
   (female ?x)
   (not (test (eq ?x ?y)))
   =>
   (assert sister
Defining defrule: predecessor 
[EXPRNPSR3] Missing function declaration for defrule.

ERROR:
(defrule MAIN::predecessor
   (or  (children ?x ?y)
        (and (children ?x ?z)
             (predecessor ?z ?y)))
   =>
   (assert (predecessor ?x ?y)
           (printout t ?x "is a predecessor to " ?y crlf))
   (defrule

Большое спасибо заранее

1 Ответ

0 голосов
/ 21 апреля 2020

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

У вас отсутствуют скобки в правилах сестры и предшественника. Их исправление позволит загружать правила без ошибок.

(defrule sister
    (children ?z ?x)
    (children ?z ?y)
    (female ?x)
    (not (test (eq ?x ?y)))
=>
    (assert (sister ?x ?y))
    (printout t ?x "is a sister to " ?y crlf))

(defrule predecessor
(or
    (children ?x ?y)
    (and (children ?x ?z)(predecessor ?z ?y))
)
=>
(assert (predecessor ?x ?y))
(printout t ?x "is a predecessor to " ?y crlf))

Эти правила по-прежнему не будут выполняться с вашим существующим кодом, поскольку они требуют наличия дочерних и женских фактов, и ни одно из ваших правил не утверждает эти факты.

Не ясно, что вы пытаетесь сделать со своим старым правилом, но, поскольку вы пытаетесь сопоставить два значения в интервале возраста, это правило вызовет ошибки, поскольку этот интервал может содержать только одно значение.

...