Пролог - Нахождение всех корней куба с числом в качестве предела
Я хочу найти все корни куба, которые их кубы + их остаток складывают в число для пользовательских входов. Так, например, запрос:
?- smallerCube(X,20).
Дал бы результат:
1 remainder 19
2 remainder 12
Так как 1^3 = 1 (остаток 19), 2^3 = 8(остаток 12) и 3^3 = 27, что больше начального значения 20, и, следовательно, здесь оно не рассчитывается.
Пока это мой код:
cubeLess(X,B,R) :-
X =< B,
X1 is X*X*X,
R is B-X1.
smallerCube(X,B) :- int(X),
X2 is X*X*X,
X2 =< B,
cubeLess(X2,B,R),
write(X), write(' rest '), writeln(R).
int(1).
int(N) :- int(N1), N is N1+1.
Я использую cubeLess, чтобы получить остаток, int, чтобы генерировать числа от 1 года. Тем не менее, когда я запускаю следующий запрос:
?- smallerCube(X,130)
Я получаю следующий странный результат:
1 rest 129
X = 1
2 rest -382
X = 2
3 rest -19553
X = 3 ;
Почему это работает для X=1, но дает отрицательные результаты для X=2,3?
Спасибо!
1 ответ
Используйте clpfd!
: - use_module ( библиотека (clpfd)).
Не нужно беспокоиться об использовании clpfd в первый раз - вы точно поймете смысл через мгновение!
меньше Cube_(X, остаток, максимум): - X #> = 0, Остаток #>= 0, Остаток + X ^ 3 # = Максимум.
Во-первых, самый общий запрос smallerCube_/3
:
? - меньший куб_ (X, остаток, 20). X в 1..2, _A в 1..8, остаток в 12..19, X^3 #= _A, остаток +_A #= 20.
Один ответ - два решения: давайте разберемся с ними!
? - меньший куб_ (X, остаток, 20), индомен (X). X = 1, остаток = 19 % 20 #= 1^3 + 19; X = 2, остаток = 12. % 20 #= 2^3 + 12
Вот второй запрос, который ОП хотел выполнить:
? - меньший куб_ (X, остаток, 130), индомен (X). X = 1, остаток = 129 % 130 #= 1^3 + 129; X = 2, остаток = 122 % 130 #= 2^3 + 122; X = 3, остаток = 103 % ...; X = 4, остаток = 66 % ...; X = 5, остаток = 5. % 130 #= 5^3 + 5
Готово! Ну и что дальше? Конечно, это зависит от вас, так что
- Почему бы не реинвестировать время, сэкономленное вами clpfd?
- Почему бы не прочитать этот очень компактный учебник для начинающих CLP(FD)?