% Graph definition 1

% vertex(a).

% edge(X, h). entails edge(everything, h)
% edge(X, h) :-
%   vertex(X).
%       (This prevents edge(gibberish, h))

edge(a, b).
edge(a, e).
edge(b, c).
edge(b, f).
edge(e, d).
edge(e, f).
edge(f, c).
edge(g, d).
edge(g, h).
edge(h, f).

edge(d, a).
edge(a, a).


% reachable(A, B) iff
% reachable by itself (base case -- reachable(X, X)
% or edge(A, B) reachable(B, C) gets reachable(A, C)

reachable(X, X).
reachable(X, Z) :-
    edge(X, Y),
    reachable(Y, Z).

% reachable2 : does not search through loops
reachable2(X, X, L).
reachable2(X, Z, L) :-
    edge(X, Y),
    notin(Y, L),
    reachable2(Y, Z, [Y|L]).

notin(X, []).
notin(X, [Y|L]) :-
    X \= Y,
    notin(X, L).
