这是问题所在。
如果我们有两个陈述
p=>q
和q=>r
,也意味着p=>r
。
给定一组语句,我需要查找给定语句是true
还是false
还是不能从给定语句中得出结论。
例:
给出陈述p=>q, p=>r, q=>s
如果输入为p=>s
我应该得到输出true
如果输入为p=>t
我应该得到输出Cannot be concluded
如果输入为p=> ~p
我应该得到输出false
这里我的问题是实现这个的最佳数据结构是什么以及使用什么算法。
感谢。
答案 0 :(得分:1)
所以,我仍然不清楚你要做什么。在被投票的风险下,我会把它踢出去,看看人们的想法。
我可以从构建图表开始。每个实体(p,q等)都有自己的节点。 “Implies”意味着您在两个节点之间画一条线。那么,任何输入只是看看你是否能找到一种遍历图形的方法 - 所以在你的例子中,a => b,b => c,图形有三个节点,一个连接到b,b连接到c。 a和c之间存在路径的事实意味着a暗示c。
我还没有进一步审查这个想法,但这似乎是一个有趣的前景。特别是因为图论很酷,很多人对它感兴趣(即Facebook高管)。并且Python中有很好的模块用于分析图形。 (我假设C ++也是如此。你可以随时使用Gephi手动指出它:https://gephi.org/)
答案 1 :(得分:1)
很多人已经研究过这个问题很多年了。你需要的是SAT Solver。查找Chaff或zChaff或任何其他常用的SAT解算器。你想要你的条款如(p-> q&& q-> r) - > (p - > r)并否定它们并确定它是否可满足。如果否定是不可满足的,那么你就有了一个定理,这个定理总是正确的。如果原条款可以满足且条款的否定是可以满足的,则您应该返回“无法结束”。如果原始条款不能令人满意,那么你就会有一些错误的东西。
这实际上是一个研究得很好的问题。有很好的算法,但是你可以处理的命题变量有很多限制。 SAT是NP难题的核心。一类未知有效算法的问题。
答案 2 :(得分:1)
我认为,考虑到问题的简单性,您可以使用简单的map
。 vector
的主要优势在于更快的查找速度。
// For "p": { name: "p", positive: "true" }
// For "~q": { name: "q", positive: "false" }
struct Predicate {
std::string _name;
bool _positive;
};
using PredicateSetType = std::unordered_set<Predicate>;
using PredicateMapType = std::unordered_map<Predicate, PredicateSetType>;
您可以通过以下方式使用地图:在给定p => q
时,您可以在与{ "q", true }
相关联的谓词集中插入{ "p", true }
。
请注意,这实际上是对有向图进行编码,因此在证明语句时,探索图的典型方法是适用的。