% data is the data set. Each data vector should be a row vector in a matrix.
% numTestUsers is the number from the data set that will be set aside and not
% used in training.
% minNumRatings is number of ratings given to the system for a test case before
% evaluation
%
% Assumptions:
% missing data is a 0.
function [logLikeRandom, lossRandom, logLikeVOI, lossVOI] = ...
testVoi(data,numTestUsers,minNumRatings,A,G,M,W,...
trainIndices,iters,numVQs,numCompsPerVQ,var_m, var_g)
%the number of data vectors
N = size(data,1);
%the dimension of each data vector
D = size(data,2)
%maxRated is the maximum number of items that a user could have voted
% upon.
maxRated = D-minNumRatings;
%Records log likelihood for the held out data for a user
logLikeRandom = zeros(numTestUsers,maxRated);
logLikeVOI = zeros(numTestUsers,maxRated);
%The loss associated with each recommendation
lossRandom = zeros(numTestUsers,maxRated);
lossVOI = zeros(numTestUsers, maxRated);
%constant representing marker for missing data.
mD=0;
%The following indices are indices to users (rows) from the data;
%temp=randperm(N);
%testIndices=temp(1:numTestUsers);
%trainIndices=temp(numTestUsers+1:end);
%
%trainData = data(trainIndices,:);
%% *model-specific* Training?
%[A,G,M,W] = MCVQ(trainData,numVQs,numCompsPerVQ,iters);
for i=1:numTestUsers
testUser = testIndices(i);
testUserRatings=data(testUser,:);
%Finding the indices to the data vector that have values (not missing)
votedOnIndices = find(testUserRatings~=mD);
%Separating the rating vector for the user to known and hidden.
temp = randperm(length(votedOnIndices));
knownIndices = votedOnIndices(temp(1:minNumRatings));
heldOutIndices = votedOnIndices(temp(minNumRatings+1:end));
numHeldOut = length(heldOutIndices);
%This vector will be the ratings for this user, except with all values
% not part of knownIndices are 0.
knownRatings = zeros(1,D);
% making a copy of testUserRatings with all but knownRatings zeroed out
for j=knownIndices knownRatings(j) = testUserRatings(j); end
%%%%%%%%%%%%%%%%%
%Testing without value of information - random selection of next movie
for numAdded = 1:numHeldOut
%% *model-specific* compute expected values for still heldOutRatings
% inferredRatings = MCVQ_infer(knownRatings,numVQs,numCompsPerVQ,...
% A,G,M,W,var_m, var_g);
inferredRatings = 5 * rand(1,D);
inferredHeldOut = zeros(1,D);
for j=heldOutIndices inferredHeldOut(j) = inferredRatings(j); end;
heldOutPdf = ratingPdf(inferredHeldOut);
%select top pick
[maxModelRating,topPick] = max(inferredHeldOut);
%record the difference between the best pick and the model's topPick
lossRandom(i,numAdded) = abs(max(testUserRatings) - maxModelRating);
%compute logLikely using the pdfs over heldOutRatings
logLikeRandom(i,numAdded) = ...
logLikelihood(heldOutPdf,testUserRatings,heldOutIndices);
%add a new rating index to knownRatings and removing it from those
% that are held out.
addedRatingIndex = heldOutIndices(1);
knownRatings(addedRatingIndex) = testUserRatings(addedRatingIndex);
knownIndices = [knownIndices addedRatingIndex];
heldOutIndices = [heldOutIndices(2:end)];
end
%%%%%%%%%%%%%%%%
%Testing with VOI -- adding heldout data to model using VOI
knownIndices = votedOnIndices(temp(1:minNumRatings));
heldOutIndices = votedOnIndices(temp(minNumRatings+1:end));
numHeldOut = length(heldOutIndices);
knownRatings = zeros(1,D);
for j=knownIndices knownRatings(j) = testUserRatings(j); end
for numAdded = 1:numHeldOut
%% *model-specific* compute expected values for still heldOutRatings
% inferredRatings = MCVQ_infer(knownRatings,numVQs,numCompsPerVQ,A,G,M,W);
inferredRatings = 5 * rand(1,D);
inferredHeldOut = zeros(1,D);
for j=heldOutIndices inferredHeldOut(j) = inferredRatings(j); end;
heldOutPdf = ratingPdf(inferredHeldOut);
%select top pick
[maxModelRating,topPick] = max(inferredHeldOut);
%record the difference between the best pick and the model's topPick
lossVOI(i,numAdded) = abs(max(testUserRatings) - maxModelRating);
%compute logLikely using the pdfs over heldOutRatings
logLikeVOI(i,numAdded) = ...
logLikelihood(heldOutPdf,testUserRatings,heldOutIndices);
%compute EVOI
evoiHeldOut = compVoi(heldOutIndices,knownRatings,heldOutPdf);
[maxEvoi,indexMaxEVOI] = max(evoiHeldOut);
%Add a new rating index to knownRatings and removing it from those
% that are held out.
knownRatings(indexMaxEVOI) = testUserRatings(indexMaxEVOI);
knownIndices = [knownIndices indexMaxEVOI];
heldOutIndices = heldOutIndices(find(heldOutIndices~=indexMaxEVOI));
end
end