这可能是本论坛常驻CUDD/BDD专家@DCTLib的问题,但如果其他人有见解,当然欢迎!
考虑给定的minterm,例如:0--0--0--0--0---11 1。
我需要单独取下每个minterm;1〃;其中P(x_i((我处理变量的概率(、0与1-P(x_-"与1。然后我在一个极小项P(x_I(。。。(1-P(x_j((,并将它们全部相加以获得顶部事件的概率。
我需要一个接一个地处理它们的原因是我正在处理会破坏内存的大文件。一旦我超过80-100个变量,你就进入了整个minterm文本文件转储大小的TB OoM。我想取下每一个minterm,将其添加到运行总和中,并在添加后删除(如果可能的话(。
希望这是清楚的,但如果不是,可能需要一些迭代。谢谢,
这里有几个选项:
a( 您似乎已经在BDD上有了一个输出为Cudd_PrintMintterm的文本文件。计算minterms值的总和实际上并不是一个CUDD问题。只需一行一行地解析,并在运行中计算总和:
std::ifstream inFile("minterms.txt");
std::string currentLine;
double sumSoFar = 0;
while (std::getline(inFile,currentLine)) {
// Process the line "currentLine"
};
if (inFile.fail()) throw "Oopsie";
但你也可以在python中做到这一点。你可能需要用这种方法来提高数值的准确性。
b( 按照描述问题的方式,不需要迭代minterms,而是可以为每个BDD节点n分配概率p(n(,并计算根BDD节点的概率。方法是将概率1分配给TRUE叶,将概率0分配给FALSE叶,并为每个内部节点(t,e,x((具有TRUE后继节点t、ELSE后继节点e和变量x(计算
p(n) = p(t)*p(x) + p(e)*(1-p(x))
那么p(根(就是你要搜索的。这种方法更优雅,但需要编写一个处理BDD结构本身的(通常是递归的(过程。这里有一个计算令人满意的分配的示例(使用封装CUDD自身类型的数据类型(:https://github.com/VerifiableRobotics/slugs/blob/master/src/BFAbstractionLibrary/BFCudd.cpp