
%% This file (print_predicates) contains predicates used
%% for printing out segments, partitions, and examples. 

%% Behaviour of many of the predicates for printing segments
%% and partitions affected by the state of program `switches'
%% i.e. whether they are on or off. 
%% 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% SEGMENTS: 
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Print out a segment 
%
% If list_features flag on, print segment as list of Feat=Val pairs 
% (possibly split across two lines, if long). 
% Otherwise print segment just as it is. 

print_seg(0):-     % boundary marker `segment' 
    write(0), !.   % always prints same. 

print_seg(Seg):-  
    get_switch_state(list_features,off), % List_features flag off, 
    write(Seg), !.                       % just print seg as it is. 

print_seg(Seg):-
    get_switch_state(list_features,on),  % List_features  flag on. 
    segment_feature_list(Seg,FVs),       % Get list of Feat=Val pairs 
    length(FVs,Len),    
    (Len < 9                             % print out F=V list. 
       -> write(FVs) 
       ;  print_split_list(FVs,Len/2)), !.

print_seg2(FVs,N,M):- 
    M =< (N / 2), !,  
    nl, write(' '), 
    print_with_commas(FVs), write(']'). 
    
print_seg2([FV|FVs],N,M):-   
    ((0 =< N, N < 1) -> (nl, write(' ')) ; true), % - formatting
    M1 is M - 1,  
    write(FV), 
    write(','), 
    print_seg2(FVs,N,M1). 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%% Print list of segments 
%
% - printing subject to switches. 

print_segment_list([]):- nl, !. 
print_segment_list([A|As]):- 
    get_switch_state(print_seg_as_candidates,off), 
    get_switch_state(show_candidates,on),  % Only this flag on. 
    nl,                                    
    print_seg(A),                          % Print seg using print_seg
    (A = 0 ->                              % - formatting
       (get_switch_state(list_features,off)
	 -> spaces(45) ; spaces(61)) 
       ; spaces(9)), 
    print_candidates(A),                   % and also print candidate I-D
    print_segment_list(As).

print_segment_list([A|As]):- 
    get_switch_state(print_seg_as_candidates,off), % Both flags off, just 
    get_switch_state(show_candidates,off),         % print using print_seg
    nl, print_seg(A),                              
    print_segment_list(As).                       
    
print_segment_list([A|As]):- 
    get_switch_state(print_seg_as_candidates,on),  % This flag on, then
    print_candidates(A),                           % only print candidate
    print_segment_list(As).                        % I-D. 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% Prints candidates for given segment
%
% A record is kept of previous macro evaluations, 
% which is used for suggesting `candidate identities'
% for segments (found by lookup_candidates predicate). 
% If non found, ?? printed instead. 

print_candidates(Seg):- 
    lookup_candidates(Seg,Cand),     % find possible candidates. 
    (Cand = [_|_] -> print_as_set(Cand) ; true), % Print candidates. 
    (Cand = []    -> write(' ?? ')      ; true), % No candidates
    (Cand = 0     -> write(' 0 ')       ; true). % Boundary marker

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% PARTITIONS: 
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Print_partition:
%
% Prints the partition P, but only if the switch
% print_partitions is set to on. Style of printing 
% depends on whether the print_seg_as_candidates
% switch is on or not. 

print_partition(P):-
    get_switch_state(print_partitions,on),  
    get_switch_state(print_seg_as_candidates,off), !, % This switch off, so just do a 
    list_print(P), nl.                                % simple list print of partition
print_partition(P):-
    get_switch_state(print_partitions,on), 
    get_switch_state(print_seg_as_candidates,on),  % This switch on, so do a fancier
    candidate_print_partition(P),!.                % `candidate print'
print_partition(_).   % catch all, especially where print_partitions switch is off. 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Prints a partition, each sequences pair on a different line, 
% but with `candidate segments' printed in place of actual
% segments. 

candidate_print_partition([]):- nl.          % finished
candidate_print_partition([[Rule,Left,Right]|P]):- % Picks out next rule+sequence pair
   nl, write(Rule),                        % print rule name
   name(Rule,Xs),                 % - for formatting
   length(Xs,Len),                % - for formatting
   NewLen is 17 - Len,            % - for formatting
   spaces(NewLen),                % - for formatting
   candidate_print_partition2(Left),    % print candidates for surface subsequence  
   write('     '),
   candidate_print_partition2(Right),   % print candidates for surface subsequence 
   candidate_print_partition(P).        % recurse. 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Prints a list of segments, as a sequence of candidate sets. 

candidate_print_partition2([]):- !,        % empty subsequence case
   write('  []  '). 
candidate_print_partition2([0]):- !,       % boundary marker case
   write(' [0]  '). 
candidate_print_partition2(Segs):- 
   write('['), 
   candidate_print_partition3(Segs),       % Segs actually a sequence of segments
   write(']'). 

% print sequence of candidate sets: 

candidate_print_partition3([]).
candidate_print_partition3([Seg|Segs]):- 
   print_candidates(Seg),                 % print candidate set for a single segment
   candidate_print_partition3(Segs).

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Print list with set brackets
%
% E.g. prints list [a,b,c] as: {a,b,c}

print_as_set(L):-
    write('{'), 
    print_with_commas(L),
    write('}'). 

print_with_commas([]). 
print_with_commas([X1,X2|Xs]):- 
    write(X1),
    write(','), 
    print_with_commas([X2|Xs]).
print_with_commas([X]):- write(X). 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Print elements of list X, 
% each on a new line.

list_print([]). 
list_print([X|Xs]):- 
    nl, 
    write(X), 
    list_print(Xs).

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% PRINT_SPLIT_LIST <list><N> 
% print list <list>, with M elements on each line, 
% where M is N rounded up to the nearest integer, 
% except last line, which may have x (1 =< x =< M)
% elements. 

print_split_list(As,N):- 
    write('['), 
    print_split_list(As,N,1), 
    write(']'), !. 

% print_split_list/3:

print_split_list([],_N,_M).  
print_split_list([A],_N,_M):-  write(A). 
print_split_list([A|As],N,M):- 
    write(A), write(','),
    (M >= N -> (nl, spaces(1), M1 = 1) 
            ;  M1 is M + 1), 
    print_split_list(As,N,M1). 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% EXAMPLES: 
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%% List all examples, both analysis and generation. 

egs:-
    egs_a, 
    nl, 
    egs_g.

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

% Print out analysis examples, in range Low to High. 
% Analysis examples (i.e. list of segments for input  
% to analysis) stored with identifying number as facts 
% of form: eg_a(IDNum,Segments). 

egs_a(Low,High):-
    write('Analysis examples: '), nl, 
    fail_drive((eg_a(N,Ex), 
                Low =< N, N =< High, 
                write(N),
                atom_length(N,Len),  
                Spaces is 7 - Len,
                spaces(Spaces), 
                write(Ex), nl)).
		
%% List all analysis examples. 

egs_a:- egs_a(1,1000000). 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%% Print out generation examples, in range Low to High. 

egs_g(Low,High):-
    write('Generation examples: '), nl, 
    fail_drive((eg_g(N,Ex), 
                Low =< N, N =< High, 
                write(N),
                atom_length(N,Len),  
                Spaces is 7 - Len,
                spaces(Spaces), 
                write(Ex), nl)).

%% List all generation examples. 

egs_g:- egs_g(1,1000000). 

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
