
make_code(N,D) :-
    atom_codes('instance-',C1),
    number_codes(N,C2),
    number_codes(D,C3),
    myappend(C1,C2,C12), myappend(C12,"-",C12a), myappend(C12a,C3,C123), myappend(C123,".lp",C123a),
    atom_codes(NOMEFILE,C123a),
    open(NOMEFILE,write,File),
    stampa(File,'%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n'),
    stampa(File,'%%%           ASP CODE for CODE('),stampa1(File,N),
    stampa(File,' , '),stampa1(File,D),stampa(File,')           %%%\n'),
    stampa(File,'%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n'),
    stampa(File,'bit(0).\nbit(1).\n'),
    stampa(File,'%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n'),
    stampa(File,'word('),
    stampazeri(File,N),
    stampa(File,').\n'),

    stampa(File,'word('),

    generalistadecrescente(0,N,Vlist1),
    M is 2*N,
    generalistadecrescente(N,M,Vlist2),
    stampalista(File,Vlist1,','),
    stampa(File,') :-\n'),
    D1 is D -1,
    genera_tuple(D1,Vlist1,Vlist2,N,File),
    generadiversi(Vlist1,Vlist2,File),
    stampa(File,'.\n'),
    stampa(File,'%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%\n'),
    stampa(File,'solutions :- k { word('),
    stampalista(File,Vlist1,','),
    stampa(File,'):\n           bit( '),
    stampalista(File,Vlist1,';'),
    stampa(File,') } k.\n'),
    stampa(File,':- not solutions.\n'),
    stampa(File,'%%%%%% Launch as (eg):\n%%%%%% lparse -c k=16 instance-X-Y.lp | smodels 1 \n'),
    close(File).


genera_tuple(0,_,_,_,_).
genera_tuple(D,L1,L2,N,File) :-
    D > 0, D1 is D -1,
    findall(Tupla,choose(D,N,Tupla),ListaTuple),
    stampatuple(ListaTuple,L1,L2,File),
    genera_tuple(D1,L1,L2,N,File).

choose(D,N,Tupla) :-
    generalistadecrescente(0,N,List),
    scegli(D,List,Tupla).

generadiversi([],[],_).
generadiversi([A|R],[B|S],File) :-
    stampa(File,'   '),
    stampa(File,'bit('),stampa(File,A),stampa(File,'),'),
    stampa(File,'bit('),stampa(File,B),stampa(File,'),'),
    stampa(File,A),stampa(File,' != '), stampa(File,B),
    ( R \= [], !, stampa(File,' , \n');
      true),
    generadiversi(R,S,File).


%%% predicati di stampa:

stampa(File,Dato) :-
    ( number(Dato),Dato > 0,!,D=Dato,stampa(File,'Var');
      number(Dato),Dato<0,!,D is -Dato;
      D = Dato),
    write(D),
    write(File,D).

stampa1(File,Dato) :-
    write(Dato),
    write(File,Dato).

stampalista(_,[],_).
stampalista(File,[A],_) :-
    stampa(File,A).
stampalista(File,[A,B|R],Symb) :-
    stampa(File,A),
    stampa(File,Symb),
    stampalista(File,[B|R],Symb).

stampazeri(File,N) :-
    genera_lista(N,0,L),
    stampalista(File,L,', ').

stampauni(File,N) :-
    genera_lista(N,-1,L),
    stampalista(File,L,', ').


stampatuple([],_,_,_).
stampatuple([Tupla|ListaTuple],L1,L2,File) :-
    stampa(File,'   not word('),
    filtraliste(Tupla,1,L1,L2,L),
    stampalista(File,L,','),
    stampa(File,'),\n'),
    stampatuple(ListaTuple,L1,L2,File).

filtraliste(_,_,[],[],[]).
filtraliste(Tupla,C,[_|R],[B|S],[B|T]) :-
    member(C,Tupla),!,
    C1 is C + 1,
    filtraliste(Tupla,C1,R,S,T).
filtraliste(Tupla,C,[A|R],[_|S],[A|T]) :-
    C1 is C + 1,
    filtraliste(Tupla,C1,R,S,T).

%%% ausiliari

genera_lista(0,_,[]).
genera_lista(M,C,[C|R]) :-
    M > 0, M1 is M - 1,
    genera_lista(M1,C,R).


generalistadecrescente(A,A,[]).
generalistadecrescente(A,N,[N|R]) :-
    N > A, N1 is N-1,
    generalistadecrescente(A,N1,R).

%%%% liste

member(X,[X|_]).
member(X,[_|R]) :-
     member(X, R).

seleziona(X,[X|R],R).
seleziona(X,[Y|R],[Y|S]) :-
     seleziona(X, R,S ).

myappend([], L, L).
myappend([X|R], L1, [X|L2]):-myappend(R,L1,L2).

%%%

scegli(0,_,[]).
scegli(D,L,[X|R]) :-
    D > 0, D1 is D -1,
    seleziona(X,L,Lrest),
    scegli(D1,Lrest,R),
    ordinata([X|R]).

ordinata([]).
ordinata([_]).
ordinata([A,B|R]) :-
   A > B,
   ordinata([B|R]).

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
