首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >我正在尝试使用DCG创建一种语言a^n b^n-1 c^n-2,但无法使succ(0)处理n

我正在尝试使用DCG创建一种语言a^n b^n-1 c^n-2,但无法使succ(0)处理n
EN

Stack Overflow用户
提问于 2018-12-03 14:34:37
回答 3查看 203关注 0票数 3
代码语言:javascript
复制
s(Count) --> a(Count), b(Count), c(Count).

a(0) --> [].
a(succ(Count)) --> [a], a(Count).

b(0) --> [].
b(succ(succ(Count))) --> [b], b(Count).

c(0) --> [].
c(succ(succ(succ(Count)))) --> [c], c(Count).

很容易创建一个像a^n b^n c^n这样的语言,对每个规则使用succ(0),但是当涉及到改变a b和c的每个块的n时,它就不起作用了。

EN

回答 3

Stack Overflow用户

发布于 2018-12-03 15:31:07

看看你的条款,比如:

代码语言:javascript
复制
c(0) --> [].
c(succ(succ(succ(Count)))) --> [c], c(Count).

请注意,您只匹配两个大小写-零个或三个字符,但是一个或两个字符呢?不过,修改c以考虑每个可接受的长度似乎是个死胡同,在您控制所有cb的地方(即在s中)指定您需要的ab的数量要容易得多。

代码语言:javascript
复制
s(succ(succ(Count))) --> a(succ(succ(Count))), b(succ(Count)), c(Count).

这自然会转化为您的规范:对于至少两个的N,接受N as、N-1 bs和N-2 cs。

现在,剩下的就很容易了:

代码语言:javascript
复制
a(0) --> [].
a(succ(Count)) --> [a], a(Count).

b(0) --> [].
b(succ(Count)) --> [b], b(Count).

c(0) --> [].
c(succ(Count)) --> [c], c(Count).

当然,您可以将它们替换为泛型子句char(Char, Count) (作为练习向左)。

代码语言:javascript
复制
?- phrase(s(succ(succ(succ(0)))), X).
X = [a, a, a, b, b, c].
票数 4
EN

Stack Overflow用户

发布于 2018-12-04 07:57:59

除了@firefrorefiddle的回答之外,我还想注意三件事。首先,当使用Peano数时,更习惯于使用函数s/1来表示后继变量,并使用单个字母(如X)来表示变量,从而获得较小的项:

代码语言:javascript
复制
s(X)            succ(Count)
s(s(X))         succ(succ(Count))
s(s(s(X)))      succ(succ(succ(Count)))
s(s(s(s(X))))   succ(succ(succ(succ(Count))))
.               .
.               .
.               .

其次,为了进一步提高可读性,最好为DCG选择一个不同的名称,可能类似于language//1而不是s//1。第三,您可以定义一个更通用的DCG,让您指定元素及其在列表中出现的次数,而不是为abc编写相同的DCG规则。把所有这些放在一起,你的DCG可能看起来像这样:

代码语言:javascript
复制
language(s(s(X))) -->
   element_frequency(a,s(s(X))),
   element_frequency(b,s(X)),
   element_frequency(c,X).

element_frequency(_E,0) -->
   [].
element_frequency(E,s(X)) -->
   [E],
   element_frequency(E,X).

在上面的代码语言中,//1对应于你的代码中的s//1,而element_frequency//2是a//1,b//1和c//1的替代。如果你查询这个DCG,你会发现它仍然产生与@firefrorefiddle的帖子中相同的答案,例如:

代码语言:javascript
复制
   ?- phrase(language(s(s(s(0)))),L).
L = [a,a,a,b,b,c]
票数 3
EN

Stack Overflow用户

发布于 2018-12-03 14:50:16

DCG的[]随时匹配。让我们把a,b,c规则颠倒过来。

代码语言:javascript
复制
s(Count) --> a(Count), b(Count), c(Count).

a(succ(Count)) --> [a], a(Count).
a(0) --> [].

b(succ(succ(Count))) --> [b], b(Count).
b(0) --> [].

c(succ(succ(succ(Count)))) --> [c], c(Count).
c(0) --> [].

:- s(N,[a,a,a,a,a,a,b,b,b,c,c],[]),writeln(N).
:- halt.
票数 -2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/53588615

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档