简体   繁体   English

水星是否支持代数谓词?

[英]Are algebraic predicates supported in Mercury?

I'm very new to Mercury and logic programming in general. 我对Mercury和逻辑编程很新。 I haven't found a numeric example like this in the docs or samples... 我没有在文档或示例中找到这样的数字示例......

Take the example predicate: 以示例谓词为例:

:- pred diffThirtyFour(float, float).
:- mode diffThirtyFour(in, out) is det.

diffThirtyFour(A,B) :-
    ( B = A + 34.0 ).

With this, A must be ground, and B is free. 有了这个,A必须被磨削,B是自由的。 What if I want A to be free and B to be ground (eg, adding mode diffThirtyFour(out,in) is det. ). 如果我希望A自由并且B要被接地(例如,添加mode diffThirtyFour(out,in) is det.mode diffThirtyFour(out,in) is det. Can this sort of algebra be performed at compile time? 这种代数可以在编译时执行吗? I could easily define another predicate, but that doesn't seem very logical... 我可以很容易地定义另一个谓词,但这似乎不合逻辑......

Update 更新

So, something like this kind of works: 所以,像这样的作品:

:- pred diffThirtyFour(float, float).
:- mode diffThirtyFour(in, out) is semidet.
:- mode diffThirtyFour(out, in) is semidet.

diffThirtyFour(A,B) :-
    ( B = A + 34.0, A = B - 34.0 ).

A little wary of the semidet , and the redundancy of the second goal. semidet有点警惕,以及第二个目标的冗余。 Is this the only way of doing it? 这是唯一的方法吗?

Update 2 更新2

This might be the answer...it issues a warning at compile time about the disjunct never having any solutions. 这可能就是答案......它在编译时发出关于从不具有任何解决方案的析取的警告。 A correct warning, but perhaps unnecessary code-smell? 一个正确的警告,但也许是不必要的代码味道? This does what I need, but if there are better solutions out there, feel free to post them... 这就是我需要的,但如果有更好的解决方案,请随意发布它们......

:- pred diffThirtyFour(float, float).
:- mode diffThirtyFour(in, out) is det.
:- mode diffThirtyFour(out, in) is det.



diffThirtyFour(A,B) :-
    ( A = B - 34.0, 
      B = A + 34.0 
    ; 
     error("The impossible happened...")
    ).

Just discovered the ability to enter different clauses for different modes . 刚刚发现了为不同模式输入不同子句的能力。 This isn't quite an algebraic solver (which I wouldn't have expected anyway), but offers the precise organizational structure I was looking for: 这不是一个代数求解器(我不会想到它),但提供了我正在寻找的精确组织结构:

:- pred diffThirtyFour(float, float).
:- mode diffThirtyFour(in, out) is det.
:- mode diffThirtyFour(out, in) is det.
:- pragma promise_pure(diffThirtyFour/2).

diffThirtyFour(A::out,B::in)  :- A = B - 34.0.
diffThirtyFour(A::in, B::out) :- B = A + 34.0.

As described in the link, the promise_pure pragma is required because this feature can be used to break semantic consistency. 如链接中所述, promise_pure编译指示是必需的,因为此功能可用于打破语义一致性。 It would also suffice to use the promise_equivalent_clauses pragma, which promises logical consistency without purity. 使用promise_equivalent_clauses pragma也足够了,它提供了逻辑一致性而没有纯度。 It is still possible to declare clauses with inconsistent semantics with the impure keyword in the pred declaration. 它仍然是有可能与不一致的语义声明条款impure在预解码申报关键字。

Interestingly, addition and subtraction in the standard int module are inversible, but not in the float module. 有趣的是,标准int模块中的加法和减法是不可逆的,但在float模块中则不然。 Perhaps the choice was made because of possible errors in floating point arithmetic.... 也许选择是因为浮点算法可能存在错误....

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM