⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 electrnc.clp

📁 NASA 开发使用的一个专家系统
💻 CLP
字号:
;;;======================================================;;;   Circuit Input/Output Simplification Expert System;;;;;;     This program simplifies the boolean decision ;;;     table for a circuit consisting of inputs (SOURCES) ;;;     and outputs (LEDs). ;;;;;;     The simplification procedure works as follows:;;;     1) The connections between components of the;;;        circuit are initialized.;;;     2) The response of the circuit when all SOURCEs;;;        are set to zero is determined.;;;     3) Source input values are changed one at a time;;;        and the response of the circuit is determined.;;;        All possible input combinations are iterated;;;        through using a gray code (a number representation;;;        system using binary digits in which successive;;;        integers differ by exactly one binary digit).;;;        For example, the gray code for the numbers 0 to 7;;;        is 0 = 000, 1 = 001, 2 = 011, 3 = 010, 4 = 110,;;;        5 = 111, 6 = 101, 7 = 100. By using a gray code,;;;        only one SOURCE has to be changed at a time to;;;        determine the next response in the decision ;;;        table (minimizing execution time).;;;     4) As responses are determined, a rule checks to;;;        see if any two sets of inputs with the same;;;        response differ if a single input. If so, then;;;        the single input can be replaced with a * ;;;        (indicating that it does not matter what the;;;        value of the input is given the other inputs).;;;        For example,  if the input 0 1 0 gave a response;;;        of 1 0 and the input 0 0 0 gave the same response,;;;        then the decision table can be simplified by;;;        indicating that 0 * 0 gives a response of 1 0.;;;     5) Once all responses and simplifications have been;;;        determined, the decision table for the circuit is;;;        printed.;;;        ;;;     This example illustrates the use of most of the;;;     constructs available in CLIPS 5.0 and also shows how;;;     COOL can be effectively integrated with rules.;;;     Generic functions are used to connect the components;;;     of the circuit during initialization. Classes,;;;     message-handlers, and deffunctions are used to;;;     determine the response of the circuit to a set of;;;     inputs. Rules, deffunctions, and global variables;;;     are used to control execution, iterate through all;;;     possible input combinations, simplify the boolean;;;     decision tree, and print out the simplified decision;;;     tree.;;;;;;     CLIPS Version 6.0 Example;;; ;;;     To execute, load this file, load one of the circuit;;;     files (circuit1.clp, circuit2.clp, or circuit3.clp), ;;;     reset, and run.;;;======================================================;;;***********;;; DEFCLASSES;;;***********(defclass COMPONENT  (is-a USER)  (slot ID# (create-accessor write)))(defclass NO-OUTPUT  (is-a USER)  (slot number-of-outputs (access read-only) (default 0)   (create-accessor read)))(defmessage-handler NO-OUTPUT compute-output ())(defclass ONE-OUTPUT  (is-a NO-OUTPUT)  (slot number-of-outputs (access read-only) (default 1)    (create-accessor read))  (slot output-1 (default UNDEFINED) (create-accessor write))  (slot output-1-link (default GROUND) (create-accessor write))  (slot output-1-link-pin (default 1) (create-accessor write)))(defmessage-handler ONE-OUTPUT put-output-1 after (?value)   (send ?self:output-1-link          (sym-cat put-input- ?self:output-1-link-pin)         ?value))(defclass TWO-OUTPUT  (is-a ONE-OUTPUT)  (slot number-of-outputs (access read-only) (default 2)     (create-accessor read))  (slot output-2 (default UNDEFINED) (create-accessor write))  (slot output-2-link (default GROUND) (create-accessor write))  (slot output-2-link-pin (default 1) (create-accessor write)))(defmessage-handler TWO-OUTPUT put-output-1 after (?value)   (send ?self:output-2-link          (sym-cat put-input- ?self:output-2-link-pin)         ?value))(defclass NO-INPUT  (is-a USER)  (slot number-of-inputs (access read-only) (default 0)     (create-accessor read)))(defclass ONE-INPUT  (is-a NO-INPUT)  (slot number-of-inputs (access read-only) (default 1)     (create-accessor read))  (slot input-1 (default UNDEFINED) (visibility public)     (create-accessor read-write))  (slot input-1-link (default GROUND) (create-accessor write))  (slot input-1-link-pin (default 1) (create-accessor write)))(defmessage-handler ONE-INPUT put-input-1 after (?value)   (send ?self compute-output))(defclass TWO-INPUT  (is-a ONE-INPUT)  (slot number-of-inputs (access read-only) (default 2)     (create-accessor read))  (slot input-2 (default UNDEFINED) (visibility public)     (create-accessor write))  (slot input-2-link (default GROUND) (create-accessor write))  (slot input-2-link-pin (default 1) (create-accessor write)))(defmessage-handler TWO-INPUT put-input-2 after (?value)   (send ?self compute-output)) (defclass SOURCE  (is-a NO-INPUT ONE-OUTPUT COMPONENT)  (role concrete)  (slot output-1 (default UNDEFINED) (create-accessor write)))(defclass SINK  (is-a ONE-INPUT NO-OUTPUT COMPONENT)  (role concrete)  (slot input-1 (default UNDEFINED) (create-accessor read-write)));;;*******************;;; NOT GATE COMPONENT;;;*******************(defclass NOT-GATE  (is-a ONE-INPUT ONE-OUTPUT COMPONENT)  (role concrete))(deffunction not# (?x) (- 1 ?x))(defmessage-handler NOT-GATE compute-output ()   (if (integerp ?self:input-1) then       (send ?self put-output-1 (not# ?self:input-1))));;;*******************;;; AND GATE COMPONENT;;;*******************(defclass AND-GATE  (is-a TWO-INPUT ONE-OUTPUT COMPONENT)  (role concrete))(deffunction and# (?x ?y)   (if (and (!= ?x 0) (!= ?y 0)) then 1 else 0))(defmessage-handler AND-GATE compute-output ()   (if (and (integerp ?self:input-1)             (integerp ?self:input-2)) then       (send ?self put-output-1 (and# ?self:input-1 ?self:input-2))));;;******************;;; OR GATE COMPONENT;;;******************(defclass OR-GATE  (is-a TWO-INPUT ONE-OUTPUT COMPONENT)  (role concrete))(deffunction or# (?x ?y)   (if (or (!= ?x 0) (!= ?y 0)) then 1 else 0))(defmessage-handler OR-GATE compute-output ()   (if (and (integerp ?self:input-1)             (integerp ?self:input-2)) then       (send ?self put-output-1 (or# ?self:input-1 ?self:input-2))));;;********************;;; NAND GATE COMPONENT;;;********************(defclass NAND-GATE  (is-a TWO-INPUT ONE-OUTPUT COMPONENT)  (role concrete))(deffunction nand# (?x ?y)   (if (not (and (!= ?x 0) (!= ?y 0))) then 1 else 0))(defmessage-handler NAND-GATE compute-output ()   (if (and (integerp ?self:input-1)             (integerp ?self:input-2)) then       (send ?self put-output-1 (nand# ?self:input-1 ?self:input-2))));;;*******************;;; XOR GATE COMPONENT;;;*******************(defclass XOR-GATE  (is-a TWO-INPUT ONE-OUTPUT COMPONENT)  (role concrete))(deffunction xor# (?x ?y)   (if (or (and (= ?x 1) (= ?y 0))          (and (= ?x 0) (= ?y 1))) then 1 else 0))(defmessage-handler XOR-GATE compute-output ()   (if (and (integerp ?self:input-1)             (integerp ?self:input-2)) then       (send ?self put-output-1 (xor# ?self:input-1 ?self:input-2))));;;*******************;;; SPLITTER COMPONENT;;;*******************(defclass SPLITTER  (is-a ONE-INPUT TWO-OUTPUT COMPONENT)  (role concrete))(defmessage-handler SPLITTER compute-output ()   (if (integerp ?self:input-1) then       (send ?self put-output-1 ?self:input-1)       (send ?self put-output-2 ?self:input-1)));;;**************;;; LED COMPONENT;;;**************(defclass LED  (is-a ONE-INPUT NO-OUTPUT COMPONENT)  (role concrete));;; Returns the current value of each LED ;;; instance in a multifield value.(deffunction LED-response ()   (bind ?response (create$))   (do-for-all-instances ((?led LED)) TRUE      (bind ?response (create$ ?response (send ?led get-input-1))))   ?response);;;***************************;;; DEFGENERICS AND DEFMETHODS;;;***************************(defgeneric connect);;; Connects a one output component to a one input component.(defmethod connect ((?out ONE-OUTPUT) (?in ONE-INPUT))    (send ?out put-output-1-link ?in)    (send ?out put-output-1-link-pin 1)   (send ?in  put-input-1-link ?out)   (send ?in  put-input-1-link-pin 1));;; Connects a one output component to one pin of a two input component.(defmethod connect ((?out ONE-OUTPUT) (?in TWO-INPUT) (?in-pin INTEGER))    (send ?out put-output-1-link ?in)   (send ?out put-output-1-link-pin ?in-pin)   (send ?in  (sym-cat put-input- ?in-pin -link) ?out)   (send ?in  (sym-cat put-input- ?in-pin -link-pin) 1));;; Connects one pin of a two output component to a one input component.(defmethod connect ((?out TWO-OUTPUT) (?out-pin INTEGER) (?in ONE-INPUT))    (send ?out (sym-cat put-output- ?out-pin -link) ?in)   (send ?out (sym-cat put-output- ?out-pin -link-pin) 1)   (send ?in put-input-1-link ?out)   (send ?in put-input-1-link-pin ?out-pin));;; Connects one pin of a two output component ;;; to one pin of a two input component.(defmethod connect ((?out TWO-OUTPUT) (?out-pin INTEGER)                    (?in TWO-INPUT) (?in-pin INTEGER))    (send ?out (sym-cat put-output- ?out-pin -link) ?in)   (send ?out (sym-cat put-output- ?out-pin -link-pin) ?in-pin)   (send ?in  (sym-cat put-input- ?in-pin -link) ?out)   (send ?in  (sym-cat put-input- ?in-pin -link-pin) ?out-pin));;;****************************;;; DEFGLOBALS AND DEFFUNCTIONS ;;;****************************(defglobal ?*gray-code* = (create$)           ?*sources* = (create$)           ?*max-iterations* = 0);;; Given the current iteration, determines the next ;;; bit in the gray code to change. ;;; Algorithm courtesy of John R. Kennedy (The BitMan).(deffunction change-which-bit (?x)   (bind ?i 1)   (while (and (evenp ?x) (!= ?x 0)) do       (bind ?x (div ?x 2))      (bind ?i (+ ?i 1)))   ?i);;; Forward declaration since the initial configuration;;; is stored in a separate file.(deffunction connect-circuit ());;;*********;;; DEFRULES;;;*********(defrule startup  =>  ;; Initialize the circuit by connecting the components  (connect-circuit)   ;; Setup the globals.   (bind ?*sources* (find-all-instances ((?x SOURCE)) TRUE))  (do-for-all-instances ((?x SOURCE)) TRUE     (bind ?*gray-code* (create$ ?*gray-code* 0)))  (bind ?*max-iterations* (round (** 2 (length ?*sources*))))  ;; Do the first response.  (assert (current-iteration 0)))(defrule compute-response-1st-time   ?f <- (current-iteration 0)   =>   ;; Set all of the sources to zero.   (do-for-all-instances ((?source SOURCE)) TRUE (send ?source put-output-1 0))   ;; Determine the initial LED response.   (assert (result ?*gray-code* =(str-implode (LED-response))))   ;; Begin the iteration process of looping through the gray code combinations.   (retract ?f)   (assert (current-iteration 1)))(defrule compute-response-other-times   ?f <- (current-iteration ?n&~0&:(< ?n ?*max-iterations*))   =>   ;; Change the gray code, saving the changed bit value.   (bind ?pos (change-which-bit ?n))   (bind ?nv (- 1 (nth ?pos ?*gray-code*)))   (bind ?*gray-code* (replace$ ?*gray-code* ?pos ?pos ?nv))   ;; Change the single changed source   (send (nth ?pos ?*sources*) put-output-1 ?nv)      ;; Determine the LED response to the input.   (assert (result ?*gray-code* =(str-implode (LED-response))))   ;; Assert the new iteration fact   (retract ?f)   (assert (current-iteration =(+ ?n 1))))(defrule merge-responses   (declare (salience 10))   ?f1 <- (result $?b  ?x $?e ?response)   ?f2 <- (result $?b ~?x $?e ?response)   =>   (retract ?f1 ?f2)   (assert (result $?b * $?e ?response)))(defrule print-header   (declare (salience -10))   =>   (assert (print-results))   (do-for-all-instances ((?x SOURCE)) TRUE (format t " %3s " (sym-cat ?x)))   (printout t " | ")   (do-for-all-instances ((?x LED)) TRUE (format t " %3s " (sym-cat ?x)))   (format t "%n")   (do-for-all-instances ((?x SOURCE)) TRUE (printout t "-----"))   (printout t "-+-")   (do-for-all-instances ((?x LED)) TRUE (printout t "-----"))   (format t "%n"))      (defrule print-result   (print-results)   ?f <- (result $?input ?response)   (not (result $?input-2 ?response-2&:(< (str-compare ?response-2 ?response) 0)))   =>   (retract ?f)   ;; Print the input from the sources.   (while (neq ?input (create$)) do      (printout t "  " (nth 1 ?input) "  ")      (bind ?input (rest$ ?input)))   ;; Print the output from the LEDs.   (printout t " | ")   (bind ?response (str-explode ?response))   (while (neq ?response (create$)) do      (printout t "  " (nth 1 ?response) "  ")      (bind ?response (rest$ ?response)))   (printout t crlf))

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -