UL/FRI/UNI-RI/MOS/Izpiti/2006-09-14-prolog

Iz E-študij, proste zakladnice študentskega znanja

< UL | FRI | UNI-RI | MOS | Izpiti
Skoči na: navigacija, iskanje

Izpit z dne Napaka: neveljaven čas
UL/FRI/UNI-RI/MOS


Čas pisanja: 90 minut.
Literatura: ni dovoljena.

1. naloga

Napišite program, ki vrne seznam neznank v podanem izrazu. Na primer klic countvars(3*x*(x+2*y-(z+y)), L) vrne L = [x,y,z]. Če se ista neznanka pojavi večkrat, jo štejete samo enkrat. [25 %]'

Rešitev

countvars(X, [X]):-
	\+number(X),
	atomic(X),
	!.
 
countvars(X,[]):-
	number(X),
	!.
 
countvars(Term, L):-
	arg(1,Term,A),
	arg(2,Term,B),
	countvars(A, L1),
	countvars(B, L2),
	conc(L1, L2, L3),
	setof(X, member(X, L3), L).

2. naloga

Kako bi prologu zastavili naslednja vprašanja? [25 %]

  • a) Koliko različnih elementov je v seznamu L?
  • b) Koliko je 1549 * 728?
  • c) Ali ne velja p(a) in hkrati velja p za kakšen element, ki ni a?
  • d) Poišči seznam L, ki vsebuje vse elemente X, za katere velja ali p(X) ali q(X)!
  • e) Ali obstaja kakšen element X, za katerega ne velja ne p(X) ne q(X)?

Rešitev

# a)
setof(X, member(X, L), _L), length(_L, N).
 
# b)
X is 1549 * 728.
 
# c)
\+ p(a), p(A), A \== a.
 
# d)
findall(X, (p(X) ; q(X)), L).
 
# e)
\+p(X), \+q(X).

3. naloga

Kaj odgovori prolog na naslednja vprašanja? Podajte vse odgovore v pravilnem vrstnem redu! [25 %]

  • a) ?- .
  • b) ?- bagof(M, month(M, DaysInMonth), L). # V bazi so dejstva: month(jan, 31), month(feb, 29), ..., month(dec, 31).
  • c) ?- .
  • d) ?- L = [1, 2, [3, 4], 5, [[6]], 7], member(X, L), \+ number(X).
  • e) ?- arg(1, conc([1,2], X, [1,2,3,4]), A).

Rešitev

# a)
Syntax error
 
# b)
DaysInMonth = 29,
L = [feb] ;
DaysInMonth = 30,
L = [apr, jun, sep, nov];
DaysInMonth = 31,
L = [jan, mar, maj, jul, avg, okt, dec] ;
no
 
# c)
Syntax error
 
# d)
L = [1, 2, [3, 4], 5, [[6]], 7],
X = [3, 4];
L = [1, 2, [3, 4], 5, [[6]], 7],
X = [[6]];
no
 
# e)
A = [1, 2];
no

4. naloga

Napišite predikat, ki iz danega seznama števil naredi in vrne dva seznama, v enem so liha, v drugem pa soda števila. Obenem poskrbi, da se duplikati izločijo. Primer: separate([2,4,1,5,2,7,7], L, S) vrne L = [1,5,7] in S = [2,4]. [25%]

Rešitev

separate([], [], []).
 
separate([H|T], L, S):-
	0 is (H mod 2),		%gre za sodo stevilo
	separate(T, L, S1),
	\+member(H, S1),	%odpravimo podvajanja
	S = [H|S1],
	!.
 
separate([H|T], L, S):-
	1 is (H mod 2),		%gre za liho stevilo
	separate(T, L1, S),
	\+member(H, L1),	%odpravimo podvajanja		
	L = [H|L1],
	!.
 
separate([_|T], L, S):-
	separate(T, L, S).

ali

separate(T, L, S) :-
	setof(X, (member(X, T), X mod 2 =:= 1), L),
	setof(X, (member(X, T), X mod 2 =:= 0), S).


Ker v običajnem prologu ni na voljo funkcija mod, je potrebno zadevo sam sprogramirati

liha(1):-!.
liha(X):- X>0, X1 is X-2,liha(X1).
 
soda(2):-!.
soda(X):- X>0, X1 is X-2,soda(X1).
 
 
separate(Seznam,L,S):- 
		setof(X,(member(X,Seznam),liha(X)),L),
		setof(X,(member(X,Seznam),soda(X)),S).

Od kod informacija, da mod ni na voljo?

Osebna orodja
Imenski prostori
Različice
Dejanja
navigacija

Tiskanje/izvoz
orodja