Prolog 程序的复杂性?
Posted
技术标签:
【中文标题】Prolog 程序的复杂性?【英文标题】:Complexity in Prolog programs? 【发布时间】:2010-12-19 03:14:55 【问题描述】:在 Prolog 中,使用回溯来解决问题。它是一种声明性范例,而不是一种命令性范例(如 C、php 或 Python)。在这种语言中,是否值得考虑复杂性?
正如某人在this question 中指出的那样,您认为问题的自然方式似乎是 O(N^2)。
【问题讨论】:
当然,我想是的。有列表,您可以遍历它们。这是递归完成的事实并不意味着我们不能说存在 O(n) 复杂度。 【参考方案1】:您绝对可以分析 Prolog 程序的复杂性,就像任何其他语言一样。您链接的那个特定问题可能是 O(n^2)。但并不是所有的 Prolog 程序都会有这种复杂性。例如,您可以在 Prolog 中轻松编写 SAT 求解器,而该问题是 NP-Complete。
【讨论】:
【参考方案2】:这完全取决于问题。
例如据我所知,对数字列表求和是 O(N)。
sum([],0).
sum(List,Total) :-
sum(List,0,Total).
sum([],Total,Total).
sum([Head|Rest],Accumulator,Total) :-
SoFar is Head + Accumulator,
sum(Rest,SoFar,Total).
唯一的动作是加法(“is”)和递归调用,它们的值都应该是 1。它们都将执行 ~ 列表中的每个项目一次,因此总操作应该是 ~ 2N,即 O(N)。
【讨论】:
【参考方案3】:分析任何语言的复杂性很重要,无论是序言还是任何命令式语言。不过我可以给你一些提示来加快你的序言程序
-
始终始终尝试使您的程序尾递归。这将确保您的程序不会耗尽堆栈。
尝试在您知道不需要任何进一步答案的程序中使用 cut and fail。
尝试使用累加器。
查看 CLPFD,它有助于大大减少搜索空间,从而加快您的程序。从本质上讲,它会在您的程序回溯之前消除错误的选择,并浪费时间探索这些选择。
始终先写出最佳结果规则。 (这实际上取决于问题,但通常最好的情况规则是第一位的)。
【讨论】:
以上是关于Prolog 程序的复杂性?的主要内容,如果未能解决你的问题,请参考以下文章