function out = lin(Xin,yin,words,titles)

%-- using the linear method
N  = 400;        % training set
s_len = 100;   % maximum # of features
max_len = min(s_len,size(Xin,2));
min_len = 45;    % minimum # of features
epsilon = .01;

Xphi = Xin;
yt   = yin;

[n d] = size(Xphi);

% ---- set the training set
Xtr = Xphi(1:N,:);
Xte = Xphi(N+1:size(Xphi,1),:);

ytr = yt(1:N);
yte = yt(N+1:size(yt,1));
tte = titles(N+1:length(titles));

% -- take a greedy approach to feature selection
cont=1;
notused = ones(1,size(Xtr,2));
idx=[];
lwinerr = Inf;

while(cont)
    idx_not = find(notused);
    werr = [];
    for i=1:length(idx_not)
        newdx = [idx idx_not(i)];
        wtmp = train(Xtr(:,newdx),ytr);
        ytmp = predict(wtmp,Xtr(:,newdx));
        werr(i) = sum(abs(ytmp - ytr));
    end;
    [winerr,windx] = min(werr);
    idx = [idx idx_not(windx)];
    notused(idx_not(windx)) = 0;
    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    fprintf('winner is %15s (%3.3d)(diff: %3.3d) | %d\n',...
        words{idx_not(windx)},winerr/n,(lwinerr-winerr),length(idx));
    %%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
    if (length(idx) > min_len) 
        if ((length(idx) < max_len) & (lwinerr-winerr > epsilon))
            lwinerr = winerr;
        else
            cont = 0;
        end;
    else
        lwinerr = winerr;
    end;    
end;

w = train(Xte(:,idx),yte);
yp = predict(w,Xte(:,idx));
ypre = starpred(yp);
bigmiss = find(abs(ypre-yte)>0.5);

out{1} = [ypre yte abs(ypre-yte)];
out{2} = words(idx);
out{3} = tte(find(abs(ypre-yte)));
out{4} = [bigmiss abs(ypre(bigmiss)-yte(bigmiss))];
out{5} = tte(bigmiss);
% [train_err test_err]
out{6} = [winerr/n mean(out{1}(:,3))];

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% -- star prediction function
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function spred = starpred(y)
% gives star prediction on the 
spred = .5 * (floor(2*y));
for i=1:length(spred)
    if spred(i)<0 spred(i) = 0; end;
end;