【发布时间】:2016-11-24 09:43:30
【问题描述】:
我读了一个小时的代码,但我无法理解问题出在哪里。我读到这个错误意味着我使用了一个我之前没有实例化的参数,但我看不到它在哪里。你能帮助我吗?
as_monomial(X, m(X, 0, [])) :- number(X), !.
as_monomial(^(Y, Z), m(1, Z, [v(Z, Y)])) :- !.
as_monomial(*(X, ^(Y, Z)), m(G, K, Q)) :- as_monomial(X, m(G, TD, Vars)), K is (TD + Z), ordina_m([v(Z, Y)| Vars], Q), !.
as_monomial(*(X, Y), m(G, K, Q)) :- as_monomial(X, m(G, TD, Vars)), K is (TD + 1), ordina_m([v(1, Y)| Vars], Q), !.
as_monomial(-(X), m(-A, Y, L)) :- as_monomial(X, m(A, Y, L)).
as_monomial(X, m(1, 1, [v(1, X)])).
ordina_m(List, Sorted) :- sort(2, @=<, List, Sorted).
ordina_poly1(List, Sorted) :- sort(2, @>=, List, Sorted).
ordina_poly2(List, Sorted) :- sort(3, @=<, List, Sorted).
is_monomial(m(_C, TD, VPs)) :- integer(TD), TD >= 0, is_list(VPs).
is_polynomial(poly(M)) :- is_list(M), foreach(member(Monomio, M), is_monomial(Monomio)).
as_polynomial(+(X, Y), poly(C)) :- as_monomial(Y, G), as_polynomial(X, poly(Gs)), inverti(G, H), inverti2(Gs, Hs), ordina_poly2([H| Hs], D), inverti2(D, F), ordina_poly1(F, C), !.
as_polynomial(-(X, Y), poly(C)) :- as_monomial(-Y, G), as_polynomial(X, poly(Gs)), inverti(G, H), inverti2(Gs, Hs), ordina_poly2([H| Hs], D), inverti2(D, F), ordina_poly1(F, C), !.
as_polynomial(X, poly([X])) :- is_monomial(X), !.
as_polynomial(X, poly([Q])) :- as_monomial(X, Q), !.
/* grado massimo */
maxdegree(Poly1, Result) :- is_polynomial(Poly1), max_degree(Poly1, Result), !.
maxdegree(Poly1, Result) :- as_polynomial(Poly1, Result1), max_degree(Result1, Result), !.
max_degree(poly([]), 0) :- !.
max_degree(poly([m(_, X, _)|Xs]), X) :- max_degree(poly(Xs), Ys), X > Ys, !.
max_degree(poly([m(_, X, _)|Xs]), Ys) :- max_degree(poly(Xs), Ys), X =< Ys, !.
/* grado minimo */
mindegree(Poly1, Result) :- is_polynomial(Poly1), min_degree(Poly1, Result), !.
mindegree(Poly1, Result) :- as_polynomial(Poly1, Result1), min_degree(Result1, Result), !.
min_degree(poly([m(_, X, _)]), X) :- !.
min_degree(poly([m(_, X, _)|Xs]), X) :- min_degree(poly(Xs), Ys), X < Ys, !.
min_degree(poly([m(_, X, _)|Xs]), Ys) :- min_degree(poly(Xs), Ys), X >= Ys, !.
inverti(m(_, _, []), m(_, _, [])) :- !.
inverti(m(X, Y, [v(W, Z)| Xs]), m(X, Y, [v(Z, W)| Ys])) :- inverti(m(X, Y, Xs), m(X, Y, Ys)), !.
inverti2([], []) :- !.
inverti2([m(X, Y, [])| Zs], [m(X, Y, [])| Ss]) :- inverti2(Zs, Ss), !.
inverti2([m(X, Y, [v(W, Z)| Xs])| Zs], [m(X, Y, [v(Z, W)| Ys])| Ss]) :- inverti2([m(X, Y, Xs)| Zs], [m(X, Y, Ys)| Ss]), !.
我不会包含 as/is_polynomial 的代码,因为我之前已经使用过它,而且我对那段代码没有任何问题。你能帮我吗? 我试过的一个例子是 maxdegree(x^5+y^500+4, R)。 (对于 mindegree 也是一样)
【问题讨论】:
-
由于我们没有
is_polynomial和as_polynomial,我们无法运行代码来查看发生了什么。在任何情况下,问题几乎肯定是在X和Ys之间的四个比较之一上:这些变量中的一个或两个必须在某一时刻未实例化。最后,您的所有规则都以删减结尾这一事实几乎可以肯定意味着您的代码存在严重错误。 -
不要看剪裁。我知道他们太多了。我将作为/is_polynomial
-
Minimal, Complete, Verifiable Example。找出重现错误所需的最少代码量。您可以使用failure slice technique 找出可以安全删除的内容,但仍然会收到错误而不是失败。
-
您正在使用的算法:
=<或is,目前是您代码中的“唾手可得的果实”。 -
您确实应该首先尝试自己调试代码。从您的顶级查询开始,查看您正在调用的谓词的定义,然后开始系统地将
fail放在搜索树的下方,直到您收到实例化错误而不是简单的false。
标签: prolog polynomials instantiation-error