Salta al contenuto
Note per Studenti Esercizio - Campionamento - rejection sampling e likelihood weighting sulla rete sprinkler (slide del corso)

Esercizio - Campionamento - rejection sampling e likelihood weighting sulla rete sprinkler (slide del corso)

Testo (slide Bayesian Networks (part 2), corso di Intelligenza Artificiale, Ing. dell'Informazione UniPD). Rete sprinkler: archi C→SC\to S, C→RC\to R, S→GS\to G, R→GR\to G (CC cielo nuvoloso, SS sprinkler, RR pioggia, GG prato bagnato); P(c)=0,5P(c)=0{,}5; P(r∣C)=0,8P(r\mid C)=0{,}8 (cc), 0,10{,}1 (¬c\neg c); P(s∣C)=0,1P(s\mid C)=0{,}1 (cc), 0,50{,}5 (¬c\neg c); P(g∣S,R)=0,95P(g\mid S,R)=0{,}95 (s,rs,r), 0,900{,}90 (s,¬rs,\neg r), 0,900{,}90 (¬s,r\neg s,r), 0,100{,}10 (¬s,¬r\neg s,\neg r).

  1. Rejection sampling. Per stimare P(Rain∣s)P(\text{Rain}\mid s) si generano 100100 campioni con il prior sampling: 7373 hanno S=falseS=\text{false} e vengono scartati; dei restanti 2727 con S=trueS=\text{true}, 88 hanno R=trueR=\text{true} e 1919 hanno R=falseR=\text{false}. Qual è la distribuzione condizionata approssimata? Confrontarla con il valore esatto.
  2. Likelihood weighting. Query P(Rain∣c,g)\mathbf P(\text{Rain}\mid c,g) con ordine topologico [C,S,R,G][C,S,R,G]: calcolare il peso di un campione e, dato il campione di 1010 eventi delle slide (tutti con CC e GG veri, S,RS,R campionati), stimare la distribuzione. L'esercizio delle slide è: verificare che i risultati siano simili alle probabilità esatte.
  3. Gibbs sampling. Per la query P(Rain∣s,g)\mathbf P(\text{Rain}\mid s,g), con stato iniziale [c,s,¬r,g][c,s,\neg r,g], calcolare le distribuzioni condizionate dei due passi dell'esempio e confrontare la stima 20/8020/80 con il valore esatto.
  4. Quiz sul Markov blanket. Qual è il Markov blanket di SS (Cloudy, Rain, GrassWet, nessuno dei precedenti)?

Soluzione

I valori esatti si ottengono con l'enumerazione (Reti bayesiane - semantica, indipendenze e inferenza esattaUna rete bayesiana è un grafo diretto aciclico (DAG) con una variabile per nodo e una tabella delle probabilità condizionate (CPT) $P(X_i\mid\text{Parents}(X_i))$ per nodo; rappresenta la congiunta come prodotto $P(x_1,\dots,x_n)=\prod_i P(x_i\mid\text{parents}(X_i))$, con molti meno numeri della tabella completa (rete dell'allarme: 10 contro 31). Tre strutture elementari: catena $X\to Y\to Z$ e fork $Y\leftarrow X\to Z$ (estremi indipendenti dato il centro), collider $X\to Z\leftarrow Y$ (indipendenti, ma dipendenti se si osserva $Z$ o un suo discendente). Modelli causali (genitori = cause) danno reti più piccole. Inferenza esatta per enumerazione: $\mathbf P(X\mid\mathbf e)=\alpha\sum_{\mathbf y}\mathbf P(X,\mathbf e,\mathbf y)$ calcolata come somma di prodotti, in profondità e da sinistra a destra; per l'allarme $\mathbf P(B\mid j,m)=\langle0{,}284;\ 0{,}716\rangle$. Molti prodotti si ripetono: l'eliminazione di variabili li salva come fattori e li riusa.Reti bayesiane - semantica, indipendenze e inferenza esatta →).

1. Rejection sampling

Stima. Si normalizza il vettore dei conteggi ⟨8,19⟩\langle8,19\rangle sui 2727 campioni accettati: P^(R∣s)=⟨8, 19⟩27=⟨0,296; 0,704⟩.\hat{\mathbf P}(R\mid s)=\frac{\langle8,\,19\rangle}{27}=\langle0{,}296;\ 0{,}704\rangle. Esatto. P(r,s)=∑cP(c)P(s∣c)P(r∣c)=0,5⋅0,1⋅0,8+0,5⋅0,5⋅0,1=0,04+0,025=0,065P(r,s)=\sum_cP(c)P(s\mid c)P(r\mid c)=0{,}5\cdot0{,}1\cdot0{,}8+0{,}5\cdot0{,}5\cdot0{,}1=0{,}04+0{,}025=0{,}065 e P(s)=0,5⋅0,1+0,5⋅0,5=0,3P(s)=0{,}5\cdot0{,}1+0{,}5\cdot0{,}5=0{,}3, quindi P(r∣s)=0,065/0,3=0,2167P(r\mid s)=0{,}065/0{,}3=0{,}2167. La stima (0,2960{,}296) è troppo alta: con soli 2727 campioni utili lo scarto tipico è 0,217⋅0,783/27=0,079\sqrt{0{,}217\cdot0{,}783/27}=0{,}079, e 0,2960{,}296 dista circa uno scarto tipico dal valore esatto. Inoltre la frazione di campioni accettati attesa è P(s)=0,3P(s)=0{,}3 (2727 su 100100: in linea). Con 10510^5 campioni la stima è 0,21270{,}2127–0,21490{,}2149 a seconda del seme, con circa 30 00030\,000 campioni accettati.

2. Likelihood weighting

Peso di un campione. Evidenza c,gc,g; si campionano SS e RR. Peso w=P(c)⋅P(g∣s,r)w=P(c)\cdot P(g\mid s,r) (il fattore P(c)=0,5P(c)=0{,}5 per CC e P(g∣parents)P(g\mid\text{parents}) per GG):

campione (s,r)(s,r) ww
¬s,r\neg s,r 0,5⋅P(g∣¬s,r)=0,5⋅0,90=0,450{,}5\cdot P(g\mid\neg s,r)=0{,}5\cdot0{,}90=0{,}45
s,rs,r 0,5⋅P(g∣s,r)=0,5⋅0,95=0,4750{,}5\cdot P(g\mid s,r)=0{,}5\cdot0{,}95=0{,}475
s,¬rs,\neg r 0,5⋅0,90=0,450{,}5\cdot0{,}90=0{,}45
¬s,¬r\neg s,\neg r 0,5⋅0,10=0,050{,}5\cdot0{,}10=0{,}05

Stima dai 1010 campioni. Le slide mostrano 66 campioni (¬s,r)(\neg s,r) con w=0,45w=0{,}45, 22 campioni (s,r)(s,r) con w=0,475w=0{,}475 e 22 campioni (¬s,¬r)(\neg s,\neg r) con w=0,05w=0{,}05: Wr=6⋅0,45+2⋅0,475=2,7+0,95=3,65,W¬r=2⋅0,05=0,10,W_{r}=6\cdot0{,}45+2\cdot0{,}475=2{,}7+0{,}95=3{,}65,\qquad W_{\neg r}=2\cdot0{,}05=0{,}10, P^(R∣c,g)=⟨3,65, 0,10⟩3,75=⟨0,9733; 0,0267⟩.\hat{\mathbf P}(R\mid c,g)=\frac{\langle3{,}65,\ 0{,}10\rangle}{3{,}75}=\langle0{,}9733;\ 0{,}0267\rangle. Esatto (enumerazione, SS nascosta): P(r,c,g)=P(c)P(r∣c)∑sP(s∣c)P(g∣s,r)=0,5⋅0,8⋅(0,1⋅0,95+0,9⋅0,90)=0,4⋅0,905=0,362,P(r,c,g)=P(c)P(r\mid c)\sum_sP(s\mid c)P(g\mid s,r)=0{,}5\cdot0{,}8\cdot(0{,}1\cdot0{,}95+0{,}9\cdot0{,}90)=0{,}4\cdot0{,}905=0{,}362, P(¬r,c,g)=0,5⋅0,2⋅(0,1⋅0,90+0,9⋅0,10)=0,1⋅0,18=0,018,P(R∣c,g)=⟨0,362; 0,018⟩/0,380=⟨0,9526; 0,0474⟩.P(\neg r,c,g)=0{,}5\cdot0{,}2\cdot(0{,}1\cdot0{,}90+0{,}9\cdot0{,}10)=0{,}1\cdot0{,}18=0{,}018,\qquad\mathbf P(R\mid c,g)=\langle0{,}362;\,0{,}018\rangle/0{,}380=\langle0{,}9526;\ 0{,}0474\rangle. La stima da 1010 campioni (0,9730{,}973) è vicina al valore esatto (0,9530{,}953). Con N=105N=10^5 il codice sotto dà 0,95330{,}9533.

3. Gibbs sampling

Variabili libere: CC e RR (evidenza s,gs,g fissata). Stato iniziale [c,s,¬r,g][c,s,\neg r,g].

  1. Ricampionare CC con blanket {S,R}\{S,R\} (genitori nessuno, figli SS e RR): P(C∣s,¬r)∝P(C)P(s∣C)P(¬r∣C)P(C\mid s,\neg r)\propto P(C)P(s\mid C)P(\neg r\mid C): per cc 0,5⋅0,1⋅0,2=0,010{,}5\cdot0{,}1\cdot0{,}2=0{,}01, per ¬c\neg c 0,5⋅0,5⋅0,9=0,2250{,}5\cdot0{,}5\cdot0{,}9=0{,}225; normalizzando, P(c∣s,¬r)=0,01/0,235=0,0426P(c\mid s,\neg r)=0{,}01/0{,}235=0{,}0426. Si estrae da ⟨0,0426; 0,9574⟩\langle0{,}0426;\ 0{,}9574\rangle: nell'esempio esce ¬c\neg c.
  2. Ricampionare RR con blanket {C,S,G}\{C,S,G\}: P(R∣¬c,s,g)∝P(R∣¬c)P(g∣s,R)P(R\mid\neg c,s,g)\propto P(R\mid\neg c)P(g\mid s,R): per rr 0,1⋅0,95=0,0950{,}1\cdot0{,}95=0{,}095, per ¬r\neg r 0,9⋅0,90=0,810{,}9\cdot0{,}90=0{,}81; P(r∣¬c,s,g)=0,095/0,905=0,105P(r\mid\neg c,s,g)=0{,}095/0{,}905=0{,}105. Nell'esempio esce rr: stato [¬c,s,r,g][\neg c,s,r,g].

Esatto. P(r,s,g)=∑cP(c)P(s∣c)P(r∣c)P(g∣s,r)=0,95⋅0,065=0,06175P(r,s,g)=\sum_cP(c)P(s\mid c)P(r\mid c)P(g\mid s,r)=0{,}95\cdot0{,}065=0{,}06175 e P(¬r,s,g)=0,90⋅(0,5⋅0,1⋅0,2+0,5⋅0,5⋅0,9)=0,90⋅0,235=0,2115P(\neg r,s,g)=0{,}90\cdot(0{,}5\cdot0{,}1\cdot0{,}2+0{,}5\cdot0{,}5\cdot0{,}9)=0{,}90\cdot0{,}235=0{,}2115: P(r∣s,g)=0,06175/0,27325=0,2260P(r\mid s,g)=0{,}06175/0{,}27325=0{,}2260. La stima delle slide (2020 volte rr su 8080 passi: 0,250{,}25) è vicina. Con 10510^5 passi dopo 10001000 di burn-in: 0,22340{,}2234.

4. Markov blanket di SS

SS ha genitore CC, figlio GG e GG ha un altro genitore, RR. Dunque il blanket è {C,R,G}\{C,R,G\} = {Cloudy,Rain,GrassWet}\{\text{Cloudy},\text{Rain},\text{GrassWet}\}: sono corrette tutte e tre le prime opzioni (e quindi "nessuna delle precedenti" è sbagliata). Per SS vale P(s∣C,R,G)∝P(s∣C)P(g∣s,R)P(s\mid C,R,G)\propto P(s\mid C)P(g\mid s,R).

Codice

python
import random

# rete sprinkler: (genitori, CPT = P(X=vero | genitori))
bn = {
    'C': ([], {(): 0.5}),
    'S': (['C'], {(True,): 0.1, (False,): 0.5}),
    'R': (['C'], {(True,): 0.8, (False,): 0.1}),
    'G': (['S', 'R'], {(True, True): 0.95, (True, False): 0.90,
                       (False, True): 0.90, (False, False): 0.10}),
}
ordine = ['C', 'S', 'R', 'G']                  # ordine topologico

def p_vero(var, val):
    genitori, cpt = bn[var]
    return cpt[tuple(val[g] for g in genitori)]

def prior_sample(rng):
    val = {}
    for x in ordine:                           # dai genitori ai figli
        val[x] = rng.random() < p_vero(x, val)
    return val

def rejection(X, ev, N, rng):
    c = {True: 0, False: 0}
    for _ in range(N):
        s = prior_sample(rng)
        if all(s[k] == v for k, v in ev.items()):   # scarta se contraddice l'evidenza
            c[s[X]] += 1
    tot = c[True] + c[False]
    return c[True] / tot, tot

def likelihood_weighting(X, ev, N, rng):
    W = {True: 0.0, False: 0.0}
    for _ in range(N):
        val, w = dict(ev), 1.0
        for x in ordine:
            p = p_vero(x, val)
            if x in ev:
                w *= p if ev[x] else 1 - p     # evidenza: si pesa, non si campiona
            else:
                val[x] = rng.random() < p      # altrimenti si campiona
        W[val[X]] += w
    return W[True] / (W[True] + W[False])

def gibbs(X, ev, N, rng, burn=1000):
    val = {x: rng.random() < 0.5 for x in ordine}
    val.update(ev)
    libere = [x for x in ordine if x not in ev]
    figli = {x: [y for y in ordine if x in bn[y][0]] for x in ordine}
    def p_cond(x):                             # P(x=vero | Markov blanket)
        pesi = []
        for v in (True, False):
            val[x] = v
            p = p_vero(x, val) if v else 1 - p_vero(x, val)
            for y in figli[x]:
                py = p_vero(y, val)
                p *= py if val[y] else 1 - py
            pesi.append(p)
        return pesi[0] / (pesi[0] + pesi[1])
    cont = 0
    for i in range(N + burn):
        x = rng.choice(libere)                 # una variabile libera alla volta
        val[x] = rng.random() < p_cond(x)
        if i >= burn:
            cont += val[X]
    return cont / N

rng = random.Random(1)
print(rejection('R', {'S': True}, 100000, rng))
print(likelihood_weighting('R', {'C': True, 'G': True}, 100000, rng))
print(gibbs('R', {'S': True, 'G': True}, 100000, rng))

Output (seme 11): (0.2127..., 30204), 0.9533..., 0.22344; valori esatti 0,21670{,}2167, 0,95260{,}9526, 0,22600{,}2260. Con altri semi cambiano le ultime cifre: ad esempio la rejection con 10510^5 campioni dà 0,21490{,}2149 (seme 33) e il likelihood weighting con 1010 campioni 0,8780{,}878 (seme 33), con 100100 campioni 0,9290{,}929, con 10001000 0,9480{,}948.

Versione ripasso

  • Rete: P(c)=0,5P(c)=0{,}5; P(r∣C)=0,8; 0,1P(r\mid C)=0{,}8;\,0{,}1; P(s∣C)=0,1; 0,5P(s\mid C)=0{,}1;\,0{,}5; P(g∣S,R)=0,95; 0,90; 0,90; 0,10P(g\mid S,R)=0{,}95;\,0{,}90;\,0{,}90;\,0{,}10.
  • Rejection (rejection samplingsi scartano i campioni incoerenti con l'evidenza e si normalizzano i conteggiInferenza approssimata nelle reti bayesiane - campionamento →): ⟨8,19⟩/27=⟨0,296; 0,704⟩\langle8,19\rangle/27=\langle0{,}296;\ 0{,}704\rangle; esatto P(r∣s)=0,065/0,3=0,2167P(r\mid s)=0{,}065/0{,}3=0{,}2167. Accettati ≈P(s)=0,3\approx P(s)=0{,}3.
  • Likelihood weighting (P(R∣c,g)\mathbf P(R\mid c,g)): w=0,5⋅P(g∣s,r)w=0{,}5\cdot P(g\mid s,r): 0,450{,}45 (¬s,r\neg s,r), 0,4750{,}475 (s,rs,r), 0,050{,}05 (¬s,¬r\neg s,\neg r). Slide: Wr=3,65W_r=3{,}65, W¬r=0,1W_{\neg r}=0{,}1, stima 0,9730{,}973; esatto 0,362/0,380=0,95260{,}362/0{,}380=0{,}9526.
  • Gibbs (P(R∣s,g)\mathbf P(R\mid s,g)): P(c∣s,¬r)=0,01/0,235=0,0426P(c\mid s,\neg r)=0{,}01/0{,}235=0{,}0426; P(r∣¬c,s,g)=0,095/0,905=0,105P(r\mid\neg c,s,g)=0{,}095/0{,}905=0{,}105; esatto 0,06175/0,27325=0,22600{,}06175/0{,}27325=0{,}2260; slide 20/80=0,2520/80=0{,}25.
  • Markov blanket di SS: {C,R,G}\{C,R,G\} (genitore, altro genitore del figlio e figlio).
  • Errori tipici: non normalizzare i pesi; dimenticare P(c)P(c) nel peso; usare nel blanket solo genitori e figli senza gli altri genitori dei figli.
  • Accettazione e precisione: con 100100 campioni la rejection ne tiene circa P(s)⋅100=30P(s)\cdot100=30 (qui 2727); lo scarto tipico della stima è 0,217⋅0,783/27=0,079\sqrt{0{,}217\cdot0{,}783/27}=0{,}079, e 0,2960{,}296 dista circa uno scarto da 0,2170{,}217. Con 10510^5 campioni: 0,21270{,}2127 (seme 11), 0,21490{,}2149 (seme 33), ≈30 000\approx30\,000 accettati.
  • Esatti da ricordare: P(r,s)=0,5⋅0,1⋅0,8+0,5⋅0,5⋅0,1=0,065P(r,s)=0{,}5\cdot0{,}1\cdot0{,}8+0{,}5\cdot0{,}5\cdot0{,}1=0{,}065; P(r,c,g)=0,5⋅0,8⋅0,905=0,362P(r,c,g)=0{,}5\cdot0{,}8\cdot0{,}905=0{,}362 e P(¬r,c,g)=0,5⋅0,2⋅0,18=0,018P(\neg r,c,g)=0{,}5\cdot0{,}2\cdot0{,}18=0{,}018; P(r,s,g)=0,95⋅0,065=0,06175P(r,s,g)=0{,}95\cdot0{,}065=0{,}06175 e P(¬r,s,g)=0,9⋅0,235=0,2115P(\neg r,s,g)=0{,}9\cdot0{,}235=0{,}2115.
  • Likelihood weighting con più campioni: N=10, 100, 1000, 105N=10,\,100,\,1000,\,10^5 (seme 33): 0,8780{,}878, 0,9290{,}929, 0,9480{,}948, 0,9520{,}952, verso 0,95260{,}9526.
  • Gibbs: si ricampiona solo CC o RR (le altre variabili sono evidenza), la scelta della variabile è casuale e ogni stato è un campione; 10510^5 passi dopo 10001000 di scarto: 0,22340{,}2234.

Esercizi su questo argomento

Teoria collegata