def _bayesian_diffuse_to_children(self, kc, dynamic=False):
     children = self.link_model.get_children(kc)
     if children:
         for child in children:
             child_parents = self.link_model.get_parents(child)
             child_parents_truthtable = truthtable(len(child_parents))
             m_pba_truthtable = [
                 np.prod([
                     self.get_mastering_probability(child_parents[i])
                     if child_parents_truthtable[j][i] else 1 -
                     self.get_mastering_probability(child_parents[i])
                     for i in range(len(child_parents))
                 ]) for j in range(len(child_parents_truthtable))
             ]
             cond_pbas = self.link_model.get_links(
                 child)['from_parents'].probability_vector
             if dynamic:
                 alpha = 0.8
                 prior_child_pba = self.get_mastering_probability(child)
                 child_m_pba = alpha * (
                             prior_child_pba + (1 - prior_child_pba) * np.dot(m_pba_truthtable, cond_pbas)) \
                                + (1 - alpha) * np.dot(m_pba_truthtable, cond_pbas)
             else:
                 child_m_pba = np.dot(m_pba_truthtable, cond_pbas)
             self.set_mastering_probability(child, child_m_pba)
             self._bayesian_diffuse_to_children(child)
 def _bayesian_diffuse_to_parents(self, kc, dynamic=False):
     parents = self.link_model.get_parents(kc)
     if parents:
         for parent in parents:
             parent_children = self.link_model.get_children(parent)
             parent_children_truthtable = truthtable(len(parent_children))
             m_pba_truthtable = [
                 np.prod([
                     self.get_mastering_probability(parent_children[i])
                     if parent_children_truthtable[j][i] else 1 -
                     self.get_mastering_probability(parent_children[i])
                     for i in range(len(parent_children))
                 ]) for j in range(len(parent_children_truthtable))
             ]
             cond_pbas = self.link_model.get_links(
                 parent)['from_children'].probability_vector
             if dynamic:
                 alpha = 0.8
                 prior_parent_pba = self.get_mastering_probability(parent)
                 parent_m_pba = alpha * (
                             prior_parent_pba + (1 - prior_parent_pba) * np.dot(m_pba_truthtable, cond_pbas)) \
                                + (1 - alpha) * np.dot(m_pba_truthtable, cond_pbas)
             else:
                 parent_m_pba = np.dot(m_pba_truthtable, cond_pbas)
             self.set_mastering_probability(parent, parent_m_pba)
             self._bayesian_diffuse_to_parents(parent, dynamic)
 def get_pc_vec(self):
     pc_vec = []
     conds = truthtable(len(self.parents) + len(self.children))
     for cond in conds:
         cond_p_prob = self.p_vec[bool_list_to_int(
             cond[:len(self.parents)])] if any(self.p_vec) else 1.
         cond_c_prob = self.c_vec[bool_list_to_int(
             cond[len(self.parents):])] if any(self.c_vec) else 1.
         print(self.p_vec, self.c_vec)
         print(cond, cond_p_prob, cond_c_prob)
         pc_vec.append(cond_p_prob * cond_c_prob)
     return pc_vec
 def set_children_conditioned_probability_vector(self,
                                                 vec=None,
                                                 step_by_step=False):
     """
     Set the conditional probability vector of KnowledgeComponent given the mastering of its children.
     :param vec: the conditional probability vector knowing the states of children given by converting the index of
     the probability vector in binary (e.g. for B, C children of A, vec is 4 length : 1st index corresponds to
     B is False, C is False ; 3rd index is B True, C False)
     :param step_by_step: if the form of linked_knowledge_component is unknown, it is possible to set conditional
     probabilities value by value.
     :return: None, only changes the value of self.probability_vector
     """
     if not step_by_step:
         assert len(vec) == 2**len(self.linked_knowledge_components), "Length of the probability vector " \
                                                                      "should be 2^n."
         self.probability_vector = vec
     else:
         combinations = truthtable(len(self.linked_knowledge_components))
         for comb in combinations:
             self.probability_vector[bool_list_to_int(comb)] = input(
                 f"Probability  {self.knowledge_component.name} knowing "
                 f"{[child.name for child in self.linked_knowledge_components]} value {comb} is :"
             )