function [topN, selectedClusters, clustConfig] = resampleIfNecessary(topN, ...
  selectedClusters, clustConfig, trainSetPos, trainAllPos, params, thisIterDir)
count = getTooSmallClustersCount(topN);
if length(topN) - count > clustConfig.reclustThresh;
  return;
end
fprintf('Need to resample now.');
fileName = [thisIterDir 'RESAMPLED.mat'];
if ~fileExists(fileName)
  [positivePatches, posFeatures, posCorrespInds, clustConfig] = ...
        getRandomPatchesFromPyramidBlackout(trainAllPos(trainSetPos), ...
        trainSetPos, params, clustConfig);
  save(fileName, 'positivePatches', 'posFeatures', 'posCorrespInds', ...
     'clustConfig');
else
  load(fileName, 'positivePatches', 'posFeatures', 'posCorrespInds', ...
     'clustConfig');
end
posCorrespImgs = trainSetPos(posCorrespInds)';
toCluster = true(1, size(posFeatures, 1));
numPatchClusters = floor(sum(toCluster) / 4);
[assignedClust, unused] = clusterPatches(numPatchClusters, ...
  posFeatures, toCluster);
maxClustId = max(assignedClust);
[goodClusters, refinedClusters, centers, clustScores] = ...
  refineClustersOverlap( ...
    assignedClust, positivePatches, posFeatures, params, posCorrespInds);
fprintf('Done refining clusters. %d clusters remaining.\n', ...
  length(goodClusters));
newSelectedClusters = goodClusters;
assignedClust = refinedClusters;
[vals, inds] = sort(clustScores, 'descend');
currentClustCount = length(topN) - count;
toSel = min(length(inds), clustConfig.maxClust - currentClustCount);
picked = inds(1 : toSel);
picked = sort(picked);
newSelectedClusters = newSelectedClusters(picked);
[memPicked, unused] = ismember(assignedClust, newSelectedClusters);
assignedClust = assignedClust(memPicked);
positivePatches = positivePatches(memPicked);
posCorrespImgs = posCorrespImgs(memPicked);
newTopN = constructNewTopN(positivePatches, ...
  posCorrespImgs, assignedClust, newSelectedClusters);
topN = [topN newTopN];
selectedClusters = [selectedClusters; ...
  clustConfig.maxClustId + newSelectedClusters'];
clustConfig.maxClustId = maxClustId;
end

function count = getTooSmallClustersCount(topN)
count = 0;
for i = 1 : length(topN)
  if length(topN{i}.meta) < 3
    count = count + 1;
  end
end
end

function topN = constructNewTopN(positivePatches, ...
  posCorrespImgs, assignedClust, selectedClusters)

topN = cell(size(selectedClusters));
for i = 1 : length(selectedClusters)
  [mem, unused] = ismember(selectedClusters(i), assignedClust);
  topN{i}.meta = positivePatches(mem);
  topN{i}.scores = zeros(size(topN{i}.meta));
  topN{i}.imgIds = posCorrespImgs(mem);
end
end

