Hello!
Megoldottam a gyakorló feladatok közül a felhőkarcolósat (4. oldal, 4.
feladat).
Az én megoldásom kicsit bővebb az emelkedő függvényhez képest: a
rejtvény egy sorára felveszi az összes szükséges korlátot.
A problémám az, hogy a rowbnd([A,B,C,D], 1, 3]) hívás semmilyen
szűkítést sem végez, csak a cimkézés szakaszában derül ki, hogy a bal
oldali épület 4 magasságú.
Kíváncsi vagyok a hivatalos megoldásra - hogyan lehetne bevetni a
tanult aritmetikai és kombinatorikus korlátokat, leegyszerűsítve és
hatékonyabbá téve a feladatot. Például a maximumszámítást elég
körülményesnek tartom három listával, és a reifikációval való
trükközéssel. Nincs olyan beépített korlát, ami segíthetne?
Peti
A forráskód:
:- use_module(library(clpfd)).
:- use_module(library(lists)).
% Felveszi a Height épülettömbre a láthatósági,
% különbözőségi és tartománykorlátokat
rowbnd(Height, VNLeft, VNRight) :-
length(Height, N),
domain(Height, 1, N),
all_distinct(Height),
heightbnd(Height, VNLeft),
reverse(Height, Height2),
heightbnd(Height2, VNRight).
% Felveszi a Height épülettömbre a baloldali láthatóságot
% definiáló korlátokat
heightbnd(Height, VisibleNum) :-
visible(Height, _MaxH, -1, Visible),
sum(Visible, #=, VisibleNum).
% visible(Height, MaxH, LastMaxH, Visible)
% MaxH[n] = max(Height[1], ... Height[n])
% LastMaxH = MaxH utolsó kitöltött eleme
% Visible[n] = 1, ha az n. épület látható, 0, ha nem
visible([], [], _, []).
visible([H|HT], [M|MT], L, [V|VT]) :-
H #> L #<=> V,
M #= V*H + (1-V)*L, % M=max(H,L)
visible(HT, MT, M, VT).