首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >BayesServer: InvalidNetworkException: Node [Knowledge]具有空分布

BayesServer: InvalidNetworkException: Node [Knowledge]具有空分布
EN

Stack Overflow用户
提问于 2018-11-05 23:09:54
回答 1查看 89关注 0票数 0

我试图建立一个动态贝叶斯网络使用BayesServer库在C#为我的Unity3D游戏。我有以下实现网络的方法

代码语言:javascript
复制
// numberOfDistractors and levelId will be used later for added complexity in modeling
void InitializeNetworkForLevel(int numberOfDistractors, int levelId)
{
    beliefNet = new BayesServer.Network();

    // add a knowledge node which is a latent variable (parameter to be learned from observed values
    KTrue = new State("KTrue");
    KFalse = new State("KFalse");
    knowledge = new Variable("Knowledge", KTrue, KFalse);
    knowledgeNode = new Node(knowledge)
    {
        TemporalType = TemporalType.Temporal // this is a time series node, hence re-used for each time slice
    };
    beliefNet.Nodes.Add(knowledgeNode);

    // add a question node, which denotes the oberved variable whether the question is answered correctly or not
    // this node has two states, namely correct or incorrect
    QTrue = new State("QTrue");
    QFalse = new State("QFalse");
    question = new Variable("Question", QTrue, QFalse);
    questionNode = new Node(question)
    {
        TemporalType = TemporalType.Temporal  // this is a time series node, hence re-used for each time slice
    };
    beliefNet.Nodes.Add(questionNode);

    // add a link from knowledge node to question node
    beliefNet.Links.Add(new Link(knowledgeNode, questionNode, 0));
    for (int i = 1; i <= 5; i++) 
        beliefNet.Links.Add(new Link(knowledgeNode, knowledgeNode, i)); // time series link (order/lag i)
    QueryNetwork(true);
}

还有另一种推理方法:

代码语言:javascript
复制
void QueryNetwork(bool isAnswerCOrrect)
{

    StateContext kTrueTime0 = new StateContext(KTrue, 0);
    StateContext kFalseTime0 = new StateContext(KFalse, 0);

    Table priorKnowledge = knowledgeNode.NewDistribution(0).Table;
    priorKnowledge[kTrueTime0] = 0.5;
    priorKnowledge[kFalseTime0] = 0.5;
    // NewDistribution does not assign the new distribution, so it still must be assigned
    knowledgeNode.Distribution = priorKnowledge;

    // the second is specified for time >= 1
    Table learnRate = knowledgeNode.NewDistribution(1).Table;
    // when specifying temporal distributions, variables which belong to temporal nodes must have times associated
    // NOTE: Each time is specified relative to the current point in time which is defined as zero, 
    // therefore the time for variables at the previous time step is -1
    StateContext kTrueTime1 = new StateContext(KTrue, -1);
    StateContext kFalseTime1 = new StateContext(KFalse, -1);
    learnRate[kTrueTime1, kTrueTime0] = 0.5;
    learnRate[kFalseTime1, kTrueTime0] = 0.5;
    learnRate[kTrueTime1, kFalseTime0] = 0.5;
    learnRate[kFalseTime1, kFalseTime0] = 0.5;
    knowledgeNode.Distributions[1] = learnRate;

    Table answerStatus = questionNode.NewDistribution().Table;
    StateContext qTrue = new StateContext(QTrue, 0);
    StateContext qFalse = new StateContext(QFalse, 0);
    answerStatus[qTrue, kTrueTime0] = 0.5;
    answerStatus[qFalse, kTrueTime0] = 0.5;
    answerStatus[qTrue, kFalseTime0] = 0.5;
    answerStatus[qFalse, kFalseTime0] = 0.5;
    questionNode.Distribution = answerStatus;

    // optional check to validate network
    beliefNet.Validate(new ValidationOptions());
    // at this point the network has been fully specified

    // we will now perform some queries on the network
    RelevanceTreeInference inference = new RelevanceTreeInference(beliefNet);
    RelevanceTreeQueryOptions queryOptions = new RelevanceTreeQueryOptions();
    RelevanceTreeQueryOutput queryOutput = new RelevanceTreeQueryOutput();

    // set some temporal evidence
    if (isAnswerCOrrect)
        inference.Evidence.Set(question, new double?[] { 1, 0 }, 0, 0, 2);
    else
        inference.Evidence.Set(question, new double?[] { 0, 1 }, 0, 0, 2);

    queryOptions.LogLikelihood = true; // only ask for this if you really need it
    inference.Query(queryOptions, queryOutput); // note that this can raise an exception (see help for details)

    Debug.Log("LogLikelihood: " + queryOutput.LogLikelihood.Value);
}

但是,在尝试用QueryNetwork方法验证网络时,我会得到以下异常:

InvalidNetworkException:节点知识具有空分布。 BayesServer.Network.Validate (BayesServer.ValidationOptions选项) (at :0) BayesNet.QueryNetwork (System.Boolean isAnswerCOrrect) (在资产/脚本/BayesNet.cs:97) BayesNet.InitializeNetworkForLevel (System.Int32 numberOfDistractors,System.Int32 levelId) (资产/脚本/BayesNet.cs:59) BayesNet.Start () (见资产/脚本/BayesNet.cs:21)

当我已经在QueryNetwork方法中指定知识节点时,它为什么说它有空分布。尽管我能够使用以下代码来修复这个问题:

代码语言:javascript
复制
ValidationOptions opt = new ValidationOptions();
opt.AllowNullDistributions = true;
// optional check to validate network
beliefNet.Validate(opt);

此外,我假设第一级的概率为50%,我将如何根据第一级的推断来改变第二级的这些值?

最后,我想构建一个类似于下图所示的网络,在这些网络中,每个级别的分心者的数量是不同的(如果太复杂的话,也可能是相同的):

EN

回答 1

Stack Overflow用户

发布于 2018-11-06 21:08:26

看起来您在添加延迟1到5,而我怀疑您只需要在潜在节点上添加滞后1。虽然推断不是必需的,但为了测试这一点,我建议在用户界面中展开网络,以检查DBN是否如您所期望的那样。请注意,仅添加滞后1并不限制时间步骤的数量,只是每个步骤只连接到前一个时间步骤。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/53163622

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档