:- module day6. :- interface. :- import_module basics. :- import_module univ. :- pred run(part::in, lines::in, univ::out) is cc_multi. :- implementation. :- import_module int. :- import_module string. :- import_module list. :- pred all_diff(list(T)::in) is semidet. all_diff([]). all_diff([X | Xs]) :- not member(X, Xs), all_diff(Xs). :- pred window(int::in, list(T)::in, int::out, list(T)::out) is nondet. window(Len, In, 0, Out) :- take(Len, In, Out). window(Len, [_|In], I + 1, Out) :- window(Len, In, I, Out). :- pred start_index(int::in, list(T)::in, int::out) is cc_nondet. start_index(Len, Input, Index) :- window(Len, Input, Index, Out), all_diff(Out). :- func length(part) = int. length(one) = 4. length(two) = 14. :- pragma no_determinism_warning(run/3). run(Part, Lines, univ(Out)) :- if Lines = [Line] then Len = length(Part), (if start_index(Len, to_char_list(Line), Out0) then Out = Len + Out0 else die("not found")) else die("bad input").