All Manuals > KnowledgeWorks and Prolog User Guide > 6 Advanced Topics

6.5 Inferencing States

An inferencing state represents all the state needed to run the forward chaining interpreter, including the object base, the current cycle number and the set of unfired instantiations. It does not include rule or context definitions or any backward chaining state information.

6.5.1 Creating and Maintaining Inferencing States

Inferencing states are first-class objects that can be created and destroyed as required. Each inferencing state must have a unique name (as compared with eql) and initially there is a single inferencing state named :default.

The function make-inferencing-state makes a new empty inferencing state. Inferencing states must be destroyed with destroy-inferencing-state when no longer needed, to release the memory that they use.

Inferencing states can be found using the function find-inferencing-state and the function list-all-inferencing-states can be used to make a list of all known inferencing states.

6.5.2 The Current Inferencing State

The value of the variable *inferencing-state* is known as the current inferencing state. Its value can be changed before calling KnowledgeWorks functions, but should not be changed within the body of a rule.

Some operations, such as object creation, slot modification, reset and infer only affect the current inferencing state. Backward chaining operations that match the object base only find objects from the current inferencing state.

Operations that change rules or contexts, such as defrule and clear-all, affect all inferencing states.

6.5.3 Uses of Inferencing States

In many cases, a single inferencing state is sufficient and the initial inferencing state named :default can be used without any special effort.

To allow several independent inferencing operations to be performed simultaneously, multiple inferencing states must be managed explicitly. Some typical situations are described below.

6.5.3.1 Multiple threads

By binding *inferencing-state* around all KnowledgeWorks operations in a thread's main function as in the example below, its value can be unique to each thread.

(defun test-1-counter (name)
  (let* ((*inferencing-state* nil)
         (step (1+ (random 10)))
         (limit (* step (+ 2000 (random 100)))))
    (unwind-protect
        (progn
          (setq *inferencing-state*
                (make-inferencing-state name))
          (make-instance 'counter
                         :value limit
                         :step step)
          (infer))
      (destroy-inferencing-state *inferencing-state*))))
 
(mp:process-run-function (format nil "Test ~D" index)
                         '()
                         'test-1-counter
                         (gensym)
6.5.3.2 Interleaved in a Single Thread

By binding *inferencing-state* around specific KnowledgeWorks operations in a function as in the example below, multiple inferencing states can be maintained within a single thread.

(defun test-stepping-single-context ()
  (let ((state1 (make-inferencing-state 'state1))
        (state2 (make-inferencing-state 'state2)))
    (unwind-protect
        (progn
          (let ((*inferencing-state* state1))
            (make-instance 'step-controller
                           :kb-name 'stepper-one-a))
          (let ((*inferencing-state* state2))
            (make-instance 'step-controller
                           :kb-name 'stepper-one-b))
          (loop repeat 10
                do
                (let ((*inferencing-state* state1))
                  (infer))
                (let ((*inferencing-state* state2))
                  (infer))))
      (destroy-inferencing-state state1)
      (destroy-inferencing-state state2))))

KnowledgeWorks and Prolog User Guide (Unix version) - 01 Dec 2021 19:35:49