идентификация образца пролога для списка номеров - PullRequest
0 голосов
/ 05 октября 2018

Поэтому я пытаюсь определить, можно ли определить список чисел как арифметическую прогрессию.Например, у меня есть список чисел [5, 10, 15, 20] Мне нужно сделать предикаты, которые идентифицируют это как арифметическую прогрессию.

Ответы [ 2 ]

0 голосов
/ 05 октября 2018

Я постараюсь дать вам основу, не выдавая полного ответа.Суть в том, что вы должны выйти в интернет или получить учебник и изучить рекурсивную обработку списка Prolog.

arith_prog([X,Y|T]) :-
    Diff #= X - Y,
    arith_prog([Y|T], Diff).

arith_prog([_], _). % A single element list is a degenerate arith prog
arith_prog([X,Y|T], Diff) :- ... (what goes here?)

Обратите внимание, что я использую CLP (FD) здесь (таким образом, оператор #=/2),Это лучший способ рассуждать с целыми числами в Прологе и обеспечивает наиболее общее решение.Если вы хотите ограничить это проверкой полностью созданных числовых списков, вы можете использовать Diff is X - Y.

0 голосов
/ 05 октября 2018

Мы можем точно узнать разницу между двумя отдельными числами:

diff_between( A, B, C):- 
    C is A - B.

Что касается списков, нам нужно объединить в последовательные элементы

pairs( G3, [A | B], C):-   % G3 is a goal expecting of 3 arguments
    append( D, [_], [A | B]),
    maplist( call(G3), B, D, C).

Теперь мы можемполучите список различий между последовательными элементами:

consec_diffs( L, Diffs):-
    pairs( diff_between, L, Diffs).
 %  pairs( G3,         [A | B], C)
 %  maplist( call(diff_between), B, D, Diffs )

% consec_diffs( [a,b,c, ..., n,m], Diffs)
% =
%              [ b,c, ..., n,m ]
%              [ a,b, ....., n ]
%             ------------------- pairwise diff_between
%      Diffs = [ ............. ]

И тогда нам просто нужно выяснить, все ли они одинаковы:

is_arith_prog( A ):-
    consec_diffs( A, [B | C]),
    maplist( =:=(B), C).

Этот ответ в основном просто имеетценность любопытства.Это делает слишком много работы потенциально.Правильный способ что-то кодировать - это выполнять как можно меньше работы и как можно быстрее прийти к выводу.В этом случае это делается простым рекурсивным определением, обрабатывающим список сверху вниз.

...