訊息

English

``````using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using ccc.set;

namespace ccc.probability
{
// 隨機源：貝氏網路 BNT 有 BEAJM 五個節點，其中 B=>A, E=>A, A=>J, A=>M 有連線，
// 節點的機率為 P(B)=0.001, P(E)=0.002，
// 連線的機率為 P(A|B,E)=0.95, P(A|B,-E)=0.94, P(A|-B,E)=0.29, P(A|-B,-E)=0.001
// P(J|A)=0.90, P(J|-A)=0.05, P(M|A)=0.70, P(M|-A)=0.01。
// 參考文獻：AIMA 教科書第二版, 圖 14.2。

public class BayesNetProblem1 : ProbProblem
{
public String vars = "B,E,A,J,M";
public Map<String, String> parents = new Map<String, String>();
public Map<String, String> values = new Map<String, String>();

public BayesNetProblem1()
{
parents["B"] = "";
parents["E"] = "";
parents["A"] = "B,E";
parents["J"] = "A";
parents["M"] = "A";

values["B"] = "b,-b";
values["E"] = "e,-e";
values["A"] = "a,-a";
values["J"] = "j,-j";
values["M"] = "m,-m";

prob("b", 0.001);
prob("e", 0.002);
prob("a|b,e", 0.95);
prob("a|b,-e", 0.94);
prob("a|-b,e", 0.29);
prob("a|-b,-e", 0.001);
prob("j|a", 0.90);
prob("j|-a", 0.05);
prob("m|a", 0.7);
prob("m|-a", 0.01);
}

public void prob(String exp, double p) { d(exp, p, "-" + exp); }

public override String generate()
{
String A,B,C,D,E;
A = PR.randomSelect("A", p("A"), "-A");
B = PR.randomSelect("B", p("B"), "-B");
C = PR.randomSelect("C", p(A)*p(B), "-C");
D = PR.randomSelect("D", p("D|" + C), "-D");
E = PR.randomSelect("E", p("D|" + C), "-E");
return A + "," + B + "," + C + "," + D + "," + E;
}

public void test()
{
var net = new BayesNetModel();
net.vars = vars; net.parents = parents; net.values = values; net.d = this;
pb.log();
}
}

public class BayesNetModel : ProbModel
{
public String vars;
public Map<String, String> parents, values;

public override double p(string exp)
{
try {
double prob = base.p(exp);
Log.log("p(" + exp + ") = " + prob);
return prob;
}
catch
{
Log.log("p(" + exp + ") = Error!");
throw new Exception();
}
}

public ProbMap enumerationAsk(String X, String e)
{
ProbMap px = new ProbMap();
String[] xvalues = values[X].split(",");
foreach (var x in xvalues)
px[x+"|"+e] = enumerateAll(vars, e+","+x);
return px.normalize();
}

public double enumerateAll(String vars, String e)
{
if (vars == "") return 1.0;
String rest = vars.tail(",");
String[] yvalues = values[Y].split(",");
IEnumerable<String> yset = e.split(",").Intersect(yvalues);
var y = yset.Count() > 0 ? yset.First() : null;
if (y != null)
return pcond(y, Y, e) * enumerateAll(rest, e);
else
{
double psum = 0.0;
foreach (var yi in yvalues)
{
psum += pcond(yi, Y, e) * enumerateAll(rest, e + "," + yi);
}
return psum;
}
}

public double pcond(String y, String Y, String e)
{
return p(y + "|" + bind(parents[Y], e));
}

public String bind(String pVars, String pValues)
{
if (pVars.Trim() == "") return "";
String[] vars = pVars.split(",");
String[] vals = pValues.split(",");
for (int i=0; i< vars.Length; i++)
{
var val = values[vars[i]].split(",").Intersect(vals);
if (val.Count() > 0)
vars[i] = val.First();
}
return vars.merge(',');
}
}
}```
```