Пример #1
0
    def eventValue_test_5(self):
        """
        Test value() method
        """

        event = Event(var=self.X, val=self.X.domain[0])
        assert(event.value(self.X) == self.X.domain[0])
Пример #2
0
    def sample(self, pre_inst=None):
        """
        Returns a random sample of the network in the form of an Event. An
        event will contain a list of tuples. Each tuple is a pair between a
        random variable and it's instance, in the form:

            >>> ret = [(X, "T"), (Y, "F")]

        :param pre_inst: Default=None. Should be a list of tuples. Each tuple
                         is a pair between a random variable and a value of
                         it's domain. That value will be the value in the
                         sample instead of leaving it to random chance.
        """

        net = self.network[:]
        inst_vars = Event()

        for i in net:
            insted = i.factor.instVar(inst_vars)
            var = i.node

            if pre_inst is not None:
                val = pre_inst.value(i.node)

            if pre_inst is None or val is None:
                val = self.pickRandomValue(var.domain, insted.values,
                                           random.random())

            inst_vars.setValue(var, val)

        return inst_vars
Пример #3
0
    def sample(self, pre_inst=None):
        """
        Returns a random sample of the network in the form of an Event. An
        event will contain a list of tuples. Each tuple is a pair between a
        random variable and it's instance, in the form:

            >>> ret = [(X, "T"), (Y, "F")]

        :param pre_inst: Default=None. Should be a list of tuples. Each tuple
                         is a pair between a random variable and a value of
                         it's domain. That value will be the value in the
                         sample instead of leaving it to random chance.
        """

        net = self.network[:]
        inst_vars = Event()

        for i in net:
            insted = i.factor.instVar(inst_vars)
            var = i.node

            if pre_inst is not None:
                val = pre_inst.value(i.node)

            if pre_inst is None or val is None:
                val = self.pickRandomValue(var.domain, insted.values,
                                           random.random())

            inst_vars.setValue(var, val)

        return inst_vars
Пример #4
0
    def eventValue_test_5(self):
        """
        Test value() method
        """

        event = Event(var=self.X, val=self.X.domain[0])
        assert (event.value(self.X) == self.X.domain[0])
Пример #5
0
    def eventVarInEvent_test_4(self):
        """
        Test varInEvent() method
        """

        event = Event(var=self.X, val=self.X.domain[0])

        assert(event.varInEvent(self.X))
        assert(not event.varInEvent(self.Y))
Пример #6
0
    def eventVarInEvent_test_4(self):
        """
        Test varInEvent() method
        """

        event = Event(var=self.X, val=self.X.domain[0])

        assert (event.varInEvent(self.X))
        assert (not event.varInEvent(self.Y))
Пример #7
0
    def eventRemoveVar_test_7(self):
        """
        Test setValue method
        """

        event = Event(var=self.X, val=self.X.domain[0])
        event.removeVar(self.X)
        event.removeVar(self.Y)  # Already not in event
        assert(not event.varInEvent(self.X))
        assert(not event.varInEvent(self.Y))
Пример #8
0
    def eventRemoveVar_test_7(self):
        """
        Test setValue method
        """

        event = Event(var=self.X, val=self.X.domain[0])
        event.removeVar(self.X)
        event.removeVar(self.Y)  # Already not in event
        assert (not event.varInEvent(self.X))
        assert (not event.varInEvent(self.Y))
Пример #9
0
    def eventSetValue_test_6(self):
        """
        Test setValue method
        """

        event = Event(var=self.X, val=self.X.domain[0])
        event.setValue(self.X, self.X.domain[1])
        event.setValue(self.Y, self.Y.domain[1])

        assert(len(event.event.keys()) == 2)
        assert(event.value(self.X) == self.X.domain[1])
        assert(event.value(self.Y) == self.Y.domain[1])
Пример #10
0
    def eventSetValue_test_6(self):
        """
        Test setValue method
        """

        event = Event(var=self.X, val=self.X.domain[0])
        event.setValue(self.X, self.X.domain[1])
        event.setValue(self.Y, self.Y.domain[1])

        assert (len(event.event.keys()) == 2)
        assert (event.value(self.X) == self.X.domain[1])
        assert (event.value(self.Y) == self.Y.domain[1])
Пример #11
0
    def eventEqual_test_10(self):
        """
        Test when two event are different in their values, one variable
        """

        tlist1 = [(self.X, self.X.domain[0])]
        tlist2 = [(self.X, self.X.domain[1])]

        event1 = Event(tlist=tlist1)
        event2 = Event(tlist=tlist2)

        assert (event1 != event2)
Пример #12
0
    def eventNotEqual_test_13(self):
        """
        Test when variables in events are not the same, two variables
        """

        tlist1 = [(self.X, self.X.domain[0]), (self.Y, self.Y.domain[0])]
        tlist2 = [(self.X, self.X.domain[0]), (self.Z, self.Z.domain[0])]

        event1 = Event(tlist=tlist1)
        event2 = Event(tlist=tlist2)

        assert (event1 != event2)
Пример #13
0
    def eventNotEqual_test_11(self):
        """
        Test when two event are different in their values, two variables
        """

        tlist1 = [(self.X, self.X.domain[0]), (self.Y, self.Y.domain[0])]
        tlist2 = [(self.X, self.X.domain[1]), (self.Y, self.Y.domain[0])]
        tlist3 = [(self.Y, self.Y.domain[0]), (self.X, self.X.domain[1])]

        event1 = Event(tlist=tlist1)
        event2 = Event(tlist=tlist2)
        event3 = Event(tlist=tlist3)

        assert (event1 != event2)
        assert (event1 != event3)
Пример #14
0
    def argmin(self):
        """
        Returns event with the lesser value

        :returns: Returns an Event object with the event that minimizes the
                  value of this factor
        """

        # Find the maximum value
        minval = self.values[0]
        index = 0
        for i, value in enumerate(self.values, 1):
            if value < minval:
                minval = value
                index = i - 1

        # Make the event
        event = []
        div = 1
        for i, var in enumerate(self.rand_vars):
            doml = len(var.domain)
            val = int(index / div) % doml
            event.append((var, var.domain[val]))
            div *= len(var.domain)

        return Event(event)
Пример #15
0
    def eventConst_test_0(self):
        """
        Empty constructor
        """

        event = Event()
        assert (event.event == {})
Пример #16
0
    def gibbsAsk(self, query_var, observed, samples_num):
        # Result is a list of counts for each value in the domain of the query
        # variable. Initialized with 0
        res = {i: 0 for i in query_var.domain}

        # Assure the observed argument is an Event
        if type(observed) != Event:
            observed = Event(observed)

        # Create non evidence variable list, which are all the variables not
        # present in the observations
        non_evidence_vars = [i for i in self.network
                             if not observed.varInEvent(i.node)]

        # Get markov blankets for each non evidence variable
        mbs = dict()
        for i in non_evidence_vars:
            mbs[i.node.name] = self.markovBlanket(i)

        # Make an initial sample
        sample = self.sample(observed)

        # Execute for samples_num samples
        for i in range(samples_num):
            for j in non_evidence_vars:
                # Get distribution P(j | mb(j))
                dist = j.factor
                for k in mbs[j.node.name]:
                    dist *= k.factor

                # Instantiate with previous sample, except for current j
                # variable
                sample.removeVar(j.node)
                dist = dist.instVar(sample)

                # Set new random value of current variable in sample
                rvalue = self.pickRandomValue(dist.rand_vars[0].domain,
                                              dist.values, random.random())
                sample.setValue(j.node, rvalue)

                # Increment count
                res[rvalue] += 1

        # Return the count list normalized
        values = [res[i] for i in query_var.domain]
        return Factor(query_var, values).normalize(query_var)
Пример #17
0
    def gibbsAsk(self, query_var, observed, samples_num):
        # Result is a list of counts for each value in the domain of the query
        # variable. Initialized with 0
        res = {i: 0 for i in query_var.domain}

        # Assure the observed argument is an Event
        if type(observed) != Event:
            observed = Event(observed)

        # Create non evidence variable list, which are all the variables not
        # present in the observations
        non_evidence_vars = [i for i in self.network
                             if not observed.varInEvent(i.node)]

        # Get markov blankets for each non evidence variable
        mbs = dict()
        for i in non_evidence_vars:
            mbs[i.node.name] = self.markovBlanket(i)

        # Make an initial sample
        sample = self.sample(observed)

        # Execute for samples_num samples
        for i in range(samples_num):
            for j in non_evidence_vars:
                # Get distribution P(j | mb(j))
                dist = j.factor
                for k in mbs[j.node.name]:
                    dist *= k.factor

                # Instantiate with previous sample, except for current j
                # variable
                sample.removeVar(j.node)
                dist = dist.instVar(sample)

                # Set new random value of current variable in sample
                rvalue = self.pickRandomValue(dist.rand_vars[0].domain,
                                              dist.values, random.random())
                sample.setValue(j.node, rvalue)

                # Increment count
                res[rvalue] += 1

        # Return the count list normalized
        values = [res[i] for i in query_var.domain]
        return Factor(query_var, values).normalize(query_var)
Пример #18
0
    def eventConst_test_3(self):
        """
        var and val
        """

        event = Event(var=self.X, val=self.X.domain[0])

        assert (len(event.event.keys()) == 1)
        assert (event.event[self.X] == self.X.domain[0])
Пример #19
0
    def eventEqual_test_9(self):
        """
        Test if two equal event are actually equal
        """

        tlist1 = [(self.X, self.X.domain[0])]
        tlist2 = [(self.X, self.X.domain[0]), (self.Y, self.Y.domain[0])]
        tlist3 = [(self.Y, self.Y.domain[0]), (self.X, self.X.domain[0])]

        event1a = Event(tlist=tlist1)
        event1b = Event(tlist=tlist1)

        event2a = Event(tlist=tlist2)
        event2b = Event(tlist=tlist2)
        event2c = Event(tlist=tlist3)

        assert (event1a == event1b)
        assert (event2a == event2b)
        assert (event2a == event2c)
Пример #20
0
    def eventConst_test_1(self):
        """
        tlist test, one element
        """

        tlist = [(self.X, self.X.domain[0])]
        event = Event(tlist=tlist)

        assert (len(event.event.keys()) == 1)
        assert (event.event[self.X] == self.X.domain[0])
Пример #21
0
    def _compute_event_prob(self, event: ppy.Event):
        HashableFac.next_id = 0

        # create factors
        factors = set()
        num_to_eliminate = 0
        for i in self.network:
            # Append factor to factors list, removing observations
            fac = self.makeFactor(i.factor, event)
            factors.add(HashableFac(fac))
            if not event.varInEvent(i.node):
                num_to_eliminate += 1

        # run variable elimination
        for n in range(0, num_to_eliminate):
            new_factor_vars = {
            }  # for each variable, the set of variables in the factor if that variable is eliminated
            factors_for_var = {
            }  # for each variable, the list of factors containing the variable
            for hfac in factors:
                fac = hfac.fac
                rvset = set(fac.rand_vars)
                for var in fac.rand_vars:
                    if var not in new_factor_vars:
                        new_factor_vars[var] = rvset.copy()
                        factors_for_var[var] = []
                    else:
                        new_factor_vars[var] = new_factor_vars[var].union(
                            rvset)
                    factors_for_var[var].append(hfac)

            # find best variable to eliminate next according to min-degree strategy
            best_var = None
            best_size = -1
            for var, s in new_factor_vars.items():
                if best_var is None or len(s) < best_size:
                    best_var = var
                    best_size = len(s)

            # eliminate the variable
            rm_factors = factors_for_var[best_var]
            new_factor = self.sumOut(best_var, rm_factors)
            factors = factors.difference(rm_factors)
            factors.add(HashableFac(new_factor))

        prod = None
        for f in factors:
            if prod is None:
                prod = f.fac
            else:
                prod = prod.mult(f.fac)
        return prod.values[0]
Пример #22
0
    def eventIter_test_8(self):
        tlist = [(self.X, self.X.domain[0]), (self.Y, self.Y.domain[0]),
                 (self.Z, self.Z.domain[0])]
        event = Event(tlist=tlist)

        iter_res = [i for i in event]

        for i in range(len(tlist)):
            if tlist[i][0].name != iter_res[i][0].name and \
               tlist[i][1] != iter_res[i][1]:
                assert (False)

        assert (True)
Пример #23
0
    def eventConst_test_2(self):
        """
        tlist test, two element
        """

        tlist = []
        tlist.append((self.X, self.X.domain[0]))
        tlist.append((self.Y, self.Y.domain[0]))

        event = Event(tlist=tlist)

        assert (len(event.event.keys()) == 2)

        assert (event.event[self.X] == self.X.domain[0])
        assert (event.event[self.Y] == self.Y.domain[0])
Пример #24
0
    # Factors representing the conditional distributions of this network
    factor_cloudy = Factor(cloudy, [0.5, 0.5])
    factor_sprinkler = Factor([sprinkler, cloudy], [0.1, 0.9, 0.5, 0.5])
    factor_rain = Factor([rain, cloudy], [0.8, 0.2, 0.2, 0.8])
    factor_wet_grass = Factor([wet_grass, rain, sprinkler],
                              [0.99, 0.01, 0.9, 0.1, 0.9, 0.1, 0.0, 1.0])

    # Actual network representation
    network = [(cloudy, factor_cloudy), (sprinkler, factor_sprinkler),
               (rain, factor_rain), (wet_grass, factor_wet_grass)]

    # Create a Bayesian Network
    BN = bn.BayesianNetwork(network)

    # Set one observation
    observed = Event(var=sprinkler, val="True")

    # Run Rejection Sample algorithm
    estimate = BN.eliminationAsk(rain, observed)
    print("P(Rain | Sprinkler=true)")
    print(estimate)

    # Run Rejection Sample algorithm
    estimate = BN.rejectionSample(rain, observed, 1000)
    print("P(Rain | Sprinkler=true)")
    print(estimate)

    # Run Gibbs Ask algorithm
    estimate = BN.gibbsAsk(rain, observed, 1000)
    print("P(Rain | Sprinkler=true)")
    print(estimate)
Пример #25
0
    # tuple, the first argument is the variable of that node, the second is the
    # distribution. Note that the nodes were place in the list at random
    network = [
        (earthq,   factor_earthq),
        (alarm,    factor_alarm),
        (john,     factor_john),
        (burglary, factor_burglary),
        (mary,     factor_mary)
    ]

    # The network object
    BN = bn.BayesianNetwork(network)

    # An event with the observations In this example the variable john was
    # observed being true. Same for variable mary
    observed = Event()
    observed.setValue(john, "True")
    observed.setValue(mary, "True")

    # Run the elimination ask algorithm (Variable Elimination) for the example.
    # Result should be approximately [0.284, 0.716]
    burglary_k_john_mary = BN.eliminationAsk(burglary, observed)

    print("P(Burglary | John=true, Mary=true)")
    print(burglary_k_john_mary)

    # Another example with the same network. The observation and query variable
    # changed, but the order of the distributions is the same. The result
    # should be approximately [0.849, 0.150]
    observed = Event(var=burglary, val="True")
    john_k_burglary = BN.eliminationAsk(john, observed)
Пример #26
0
    def instNode(self, event):
        """
        Makes observation over a network creating a new network in which every
        factor containing one of the observed variables gets instantiated

        Supposing the network (The edges would be "pointing" from top to bottom
        since this is a Bayesian Network)::

            X  Y
            |\ |
            | A
            |/ |
            W  Z

        The factors that describe this network are the following::

            P(X)        = f(X)
            P(Y)        = f(Y)
            P(A | X, Y) = f(A, X, Y)
            P(W | X, A) = f(W, X, A)
            P(Z | A)    = f(Z, A)

        If the A variable is observed, every factor will have its A variable
        instantiated and the network will be composed of the following factors,
        which don't have any A variable::

            f(X)
            f(Y)
            f(A=a, X, Y) = f'(X, Y)
            f(W, X, A=a) = f'(W, X)
            f(Z, A=a)    = f'(Z)

        Or similarly, if X is instantiated::

            f(X=x)       = scalar
            f(Y)
            f(A, X=x, Y) = f'(A, Y)
            f(W, X=x, A) = f'(W, A)
            f(Z, A)      = f'(Z, A)

        Note that the node which only contained X will be reduced to a single
        scalar value.
        """

        # Resulting network list
        res_network = []

        # Assure the event argument is an Event object
        if type(event) != Event:
            event = Event(event)

        # Take each node and instantiate it's factor according to the event
        for i in self.network:
            new_node = BayesianNetworkNode(i.node, i.factor.instVar(event))
            new_node.parents = i.parents
            res_network.append(new_node)

        # Create the network and place the new list directly in the
        # attribute because it is already sorted
        res = BayesianNetwork()
        res.network = res_network
        return res