Prolog中的Sierpinski Carpet

时间:2018-03-21 16:31:23

标签: recursion prolog

看到这个问题here,因为我是一个新手,我尝试了一个不成功的解决方案。到目前为止,我已经设法做到了这一点:

rewrite('X', [['X','X','X'],['X',' ','X'],['X','X','X']]).
rewrite(' ', [[' ',' ',' '],[' ',' ',' '],[' ',' ',' ']]).

rec(1, [], CurrentList, [CurrentList]).
rec(_, [], CurrentList, CurrentList).
rec(0, L, CurrentList, Result):- append(CurrentList, [L], Result).

rec(N, [H|T], CurrentList, Result):-
    atom(H),
    N > 0,
    rewrite(H, L),
    K is N - 1,
    rec(K, L, CurrentList, Temp),
    rec(N, T, Temp, Result).

rec(N, [H|T], CurrentList, Result):-
    N > 0,
    rec(N, H, CurrentList, Temp),
    rec(N, T, Temp, Result).

carpet(N):-
    N > 0,
    rewrite(Item, _),!,
    rec(N, [[Item]], [], Result),
    write(Result).

基本上,我尝试扩展我的第一个元素,然后展开前一个扩展创建的每个元素。

然后我编写了第一个事实,即基本上是将上一个扩展的所有扩展元素放在列表中,并指示放置换行符的信号,但是从下一个扩展组的开头到结尾放置括号而不是从下一个扩展组的开始到它的结束。

我可能有很多错误的逻辑,所以任何其他解决这个问题的方法都会受到欢迎。

1 个答案:

答案 0 :(得分:2)

使用rec作为谓词名称,您并没有帮忙。该怎么办?

这是我的方法。它基于首先简化问题,仅考虑一个级别的一个非空行符号的重写。通过迭代,可以简单地考虑几行。

% expand_row(Row, Expansion): Row is a list of symbols representing one row
% of the Sierpinski carpet. Expansion is a list of rows, i.e., a list of
% lists of symbols, resulting from rewriting each symbol in Row.
expand_row([C], Expansion) :-
    rewrite(C, Expansion).
expand_row([C,D|Cs], Expansion) :-
    rewrite(C, ExpansionC),
    expand_row([D|Cs], ExpansionRest),
    maplist(append, ExpansionC, ExpansionRest, Expansion).

carpet_(1, [['X']]).
carpet_(N, Carpet) :-
    N > 1,
    N1 is N - 1,
    carpet_(N1, Carpet1),
    maplist(expand_row, Carpet1, CarpetExpanded),
    % remove one level of nesting
    append(CarpetExpanded, Carpet).

请注意,这只会计算地毯,不会打印。分别做得更好:

write_row(Row) :-
    maplist(write, Row),
    nl.

write_carpet(Carpet) :-
    maplist(write_row, Carpet).

carpet(N) :-
    carpet_(N, Carpet),
    write_carpet(Carpet).

测试:

?- between(1, 4, N), carpet(N).
X
N = 1 ;
XXX
X X
XXX
N = 2 ;
XXXXXXXXX
X XX XX X
XXXXXXXXX
XXX   XXX
X X   X X
XXX   XXX
XXXXXXXXX
X XX XX X
XXXXXXXXX
N = 3 ;
XXXXXXXXXXXXXXXXXXXXXXXXXXX
X XX XX XX XX XX XX XX XX X
XXXXXXXXXXXXXXXXXXXXXXXXXXX
XXX   XXXXXX   XXXXXX   XXX
X X   X XX X   X XX X   X X
XXX   XXXXXX   XXXXXX   XXX
XXXXXXXXXXXXXXXXXXXXXXXXXXX
X XX XX XX XX XX XX XX XX X
XXXXXXXXXXXXXXXXXXXXXXXXXXX
XXXXXXXXX         XXXXXXXXX
X XX XX X         X XX XX X
XXXXXXXXX         XXXXXXXXX
XXX   XXX         XXX   XXX
X X   X X         X X   X X
XXX   XXX         XXX   XXX
XXXXXXXXX         XXXXXXXXX
X XX XX X         X XX XX X
XXXXXXXXX         XXXXXXXXX
XXXXXXXXXXXXXXXXXXXXXXXXXXX
X XX XX XX XX XX XX XX XX X
XXXXXXXXXXXXXXXXXXXXXXXXXXX
XXX   XXXXXX   XXXXXX   XXX
X X   X XX X   X XX X   X X
XXX   XXXXXX   XXXXXX   XXX
XXXXXXXXXXXXXXXXXXXXXXXXXXX
X XX XX XX XX XX XX XX XX X
XXXXXXXXXXXXXXXXXXXXXXXXXXX
N = 4 ;
false.