Removing extra pixels after shrinking to a point and selecting the correct pixel as the cross point with Matlab
link text
Based on the link above, I managed to get the cross point but sometimes I get 2 or more results. I have 10 similar images with the cross slightly moved in every frame. Is there a way that I can remove the extra pixels remaining that are very off from the other 9 images by comparing it to the cross point of the 1st image? As the movement is quite small, is it right to say that the pixel that should be selected开发者_C百科 from the 2 or more results that I obtained should be the one that has the closest value that I have from the pixel of the previous image? Is there a way to do this? Thanks!
Yes. You could try to perform an outlier detection on the coordinates. This requires that the largest accumulation of coordinates is at the true center of the cross. From what you describe, this assumption is satisfied.
%# Assume the cross should be around [0,0],
%# and you are storing the coordinates in a cell array
coordCell = {[0,0],[0.1,-0.05;4,4],[0.3,0.2;-2,5],[-0.25,0;2,-3]};
%# collect the coordinates of all images
allCoords = cat(1,coordCell{:});
%# take the median
medCoord = median(allCoords,1);
%# calculate the residuals, take the median of them
res2 = bsxfun(@minus,allCoords,medCoord).^2;
medRes = median(res2,1);
%# outliers are some factor above the median residual
%# Rousseeuw & Leroy, 1987, calculated how much for us (1.4826).
%# The factor k is the stringency (how many 'sigmas' do you have
%# to be away from the median to be counted an outlier)
%# A common value for k is 3.
k = 3;
testValue = bsxfun(@rdivide,res2,medRes*1.4826^2);
outlierIdx = any(testValue>k^2,2);
%# now you can throw out the outliers
allCoords(outlierIdx,:) = [];
When you get one result, are you confident that it's correct? If so, you could do something like:
function pos = ChoosePosition(posGood, posA, posB)
%# posGood is the known good answer, posA and posB are candidates
if norm(posA - posGood) > norm(posB - posGood)
pos = posB;
else
pos = posA;
If you want to automate everything, you could collect up all the measurements into an Nx2 matrix and do the following:
function [dist, idx] = RankPositions(pos)
%# pos should be an Nx2 matrix of x,y candidate positions
dist = pos - repmat(mean(pos), length(pos), 1); %# this is for octave, matlab might handle pos - mean(pos)
dist = norm(dist, 'rows');
[dist, idx] = sort(dist);
%# one liner:
%# [dist, idx] = sort(norm(pos - repmat(mean(pos), length(pos), 1)), 'rows'));
This will give you a ranked assortment of the distance of each point from the average of all the points. Then, since you know you have (for instance) 10 images but got 14 (or whatever) results, you can just take the 10 lowest distances as the true positions:
realpos = pos(idx(1:10));
精彩评论