<commit_before>;; =====================================================================
;; ImplicationImplicantConjunctionRule
;;
;; ImplicationLink <TV1>
;;    A
;;    C
;; ImplicationLink <TV2>
;;    B
;;    C
;; |-
;; ImplicationLink <TV>
;;    AndLink
;;       A
;;       B
;;    C
;;----------------------------------------------------------------------

(load "formulas.scm")

(define implication-implicant-conjunction-variables
  (VariableList
     (TypedVariable
        (Variable "$A")
        (TypeChoice
           (Type "PredicateNode")
           (Type "LambdaLink")))
     (TypedVariable
        (Variable "$B")
        (TypeChoice
           (Type "PredicateNode")
           (Type "LambdaLink")))
     (TypedVariable
        (Variable "$C")
        (TypeChoice
           (Type "PredicateNode")
           (Type "LambdaLink")))))

(define implication-implicant-conjunction-body
  (AndLink
     (ImplicationLink
        (VariableNode "$A")
        (VariableNode "$C"))
     (ImplicationLink
        (VariableNode "$B")
        (VariableNode "$C"))
     (NotLink (EqualLink (VariableNode "$A") (VariableNode "$B")))))

(define implication-implicant-conjunction-rewrite
  (ExecutionOutput
     (GroundedSchema "scm: implication-implicant-conjunction-formula")
     (List
        (VariableNode "$A")
        (VariableNode "$B")
        (VariableNode "$C")
        (ImplicationLink
           (VariableNode "$A")
           (VariableNode "$C"))
        (ImplicationLink
           (VariableNode "$B")
           (VariableNode "$C"))
        (Implication
           (And
              (Variable "$A")
              (Variable "$B"))
           (Variable "$C")))))

(define implication-implicant-conjunction-rule
  (Bind
     implication-implicant-conjunction-variables
     implication-implicant-conjunction-body
     implication-implicant-conjunction-rewrite))

;; Computing the strength is based on
;;
;;    P(C|A) = P(C,A)/P(A)
;;    P(C|B) = P(C,B)/P(B)
;;
;; By Bayes rule
;;
;;    P(C|A,B) = P(A,B|C) * P(C) / P(A,B)
;;
;; Let's assume that A and B are independent, as well as independent
;; when conditioned by C, that is
;;
;;    P(A,B) = P(A) * P(B)
;;    P(A,B|C) = P(A|C) * P(B|C)
;;
;; Thus
;;
;;    P(C|A,B) = P(A|C) * P(B|C) * P(C) / (P(A) * P(B))
;;
;; By Bayes rule
;;
;;    P(A|C) = P(C|A) * P(A) / P(C)
;;    P(B|C) = P(C|B) * P(B) / P(C)
;;
;; Thus
;;
;;    P(C|A,B) = P(C|A) * P(C|B) / P(C)
;;
;; TODO: there is something weird, if P(C) is tiny then P(C|A,B) goes
;; above 1, we need to understand why. Meanwhile, we just cap at 1.
(define (implication-implicant-conjunction-formula A B C AC BC ABC)
  (let* 
      ((sA (cog-stv-strength A))
       (sB (cog-stv-strength B))
       (sC (cog-stv-strength C))
       (sAC (cog-stv-strength AC))
       (sBC (cog-stv-strength BC))
       (cAC (cog-stv-confidence AC))
       (cBC (cog-stv-confidence BC)))
    (if
       (and
           (conditional-probability-consistency sA sC sAC)
           (conditional-probability-consistency sB sC sBC))
       ;; Consistency is met build the resulting implication
       (cog-set-tv!
          ABC
          (stv (implication-implicant-conjunction-strength sC sAC sBC)
               (implication-implicant-conjunction-confidence cAC cBC)))
       ;; Inconsistent, better not build anything
       (cog-undefined-handle))))

(define (implication-implicant-conjunction-strength sC sAC sBC)
  (min (/ (* sAC sBC) sC) 1))

(define (implication-implicant-conjunction-confidence cAC cBC)
  (min cAC cBC))

; Name the rule
(define implication-implicant-conjunction-rule-name
  (DefinedSchemaNode "implication-implicant-conjunction-rule"))
(DefineLink implication-implicant-conjunction-rule-name
  implication-implicant-conjunction-rule)<commit_msg>Have implication-implicant-conjunction-rule also update the conjunction TV<commit_after>;; =====================================================================
;; ImplicationImplicantConjunctionRule
;;
;; ImplicationLink <TV1>
;;    A
;;    C
;; ImplicationLink <TV2>
;;    B
;;    C
;; |-
;; ImplicationLink <TV>
;;    AndLink
;;       A
;;       B
;;    C
;;----------------------------------------------------------------------

(load "formulas.scm")

(define implication-implicant-conjunction-variables
  (VariableList
     (TypedVariable
        (Variable "$A")
        (TypeChoice
           (Type "PredicateNode")
           (Type "LambdaLink")))
     (TypedVariable
        (Variable "$B")
        (TypeChoice
           (Type "PredicateNode")
           (Type "LambdaLink")))
     (TypedVariable
        (Variable "$C")
        (TypeChoice
           (Type "PredicateNode")
           (Type "LambdaLink")))))

(define implication-implicant-conjunction-body
  (AndLink
     (ImplicationLink
        (VariableNode "$A")
        (VariableNode "$C"))
     (ImplicationLink
        (VariableNode "$B")
        (VariableNode "$C"))
     (NotLink (EqualLink (VariableNode "$A") (VariableNode "$B")))))

(define implication-implicant-conjunction-rewrite
  (ExecutionOutput
     (GroundedSchema "scm: implication-implicant-conjunction-formula")
     (List
        (VariableNode "$A")
        (VariableNode "$B")
        (VariableNode "$C")
        (ImplicationLink
           (VariableNode "$A")
           (VariableNode "$C"))
        (ImplicationLink
           (VariableNode "$B")
           (VariableNode "$C"))
        (Implication
           (And
              (Variable "$A")
              (Variable "$B"))
           (Variable "$C")))))

(define implication-implicant-conjunction-rule
  (Bind
     implication-implicant-conjunction-variables
     implication-implicant-conjunction-body
     implication-implicant-conjunction-rewrite))

;; Computing the strength is based on
;;
;;    P(C|A) = P(C,A)/P(A)
;;    P(C|B) = P(C,B)/P(B)
;;
;; By Bayes rule
;;
;;    P(C|A,B) = P(A,B|C) * P(C) / P(A,B)
;;
;; Let's assume that A and B are independent, as well as independent
;; when conditioned by C, that is
;;
;;    P(A,B) = P(A) * P(B)
;;    P(A,B|C) = P(A|C) * P(B|C)
;;
;; Thus
;;
;;    P(C|A,B) = P(A|C) * P(B|C) * P(C) / (P(A) * P(B))
;;
;; By Bayes rule
;;
;;    P(A|C) = P(C|A) * P(A) / P(C)
;;    P(B|C) = P(C|B) * P(B) / P(C)
;;
;; Thus
;;
;;    P(C|A,B) = P(C|A) * P(C|B) / P(C)
;;
;; TODO: there is something weird, if P(C) is tiny then P(C|A,B) goes
;; above 1, we need to understand why. Meanwhile, we just cap at 1.
(define (implication-implicant-conjunction-formula A B C AC BC ABC)
  (let* 
      ((sA (cog-stv-strength A))
       (sB (cog-stv-strength B))
       (sC (cog-stv-strength C))
       (sAC (cog-stv-strength AC))
       (sBC (cog-stv-strength BC))
       (cA (cog-stv-confidence A))
       (cB (cog-stv-confidence B))
       (cC (cog-stv-confidence C))
       (cAC (cog-stv-confidence AC))
       (cBC (cog-stv-confidence BC)))
    (if
       (and
           (conditional-probability-consistency sA sC sAC)
           (conditional-probability-consistency sB sC sBC))
       ;; Consistency is met build the resulting implication
       (let ((AnB (gar ABC)))
         (cog-set-tv! AnB (stv (* sA sB) (min cA cB)))
         (cog-set-tv!
            ABC
            (stv (implication-implicant-conjunction-strength sC sAC sBC)
                 (implication-implicant-conjunction-confidence cAC cBC))))
       ;; Inconsistent, better not build anything
       (cog-undefined-handle))))

(define (implication-implicant-conjunction-strength sC sAC sBC)
  (min (/ (* sAC sBC) sC) 1))

(define (implication-implicant-conjunction-confidence cAC cBC)
  (min cAC cBC))

; Name the rule
(define implication-implicant-conjunction-rule-name
  (DefinedSchemaNode "implication-implicant-conjunction-rule"))
(DefineLink implication-implicant-conjunction-rule-name
  implication-implicant-conjunction-rule)
{'fraction_non_alphanumeric': 0.18933161953727506, 'fraction_numerical': 0.0012853470437017994, 'mean_word_length': 2.456685917370058, 'pattern_counts': {'":': 0, '<': 9, '<?xml version=': 0, '>': 9, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '3107199', 'n_tokens_mistral': 2772, 'n_tokens_neox': 2649, 'n_words': 586}