Hello, I want to limit the number of coordinates generated by the method bwboundaries or boundary while having the same step size.
1 visualización (últimos 30 días)
Mostrar comentarios más antiguos
Joumana
el 3 de Mayo de 2023
Comentada: Mathieu NOE
el 9 de Mayo de 2023
[b1,l1] = bwboundaries(Image1_seuil,'noholes');
[b2,l2] = bwboundaries(Image2_seuil,'noholes');
hold on
% Coordinates
% I want to have the same array size for x1, x2, y1 and y2
x1=[];
y1=[];
x2=[];
y2=[];
for k1 = 1:length(b1)
boundary1 = b1{k1};
plot(boundary1(:,2), boundary1(:,1), 'r', 'LineWidth', 1)
x1 = [x1; boundary1(:,2)];
y1 = [y1; boundary1(:,1)];
end
for k2 = 1:length(b2)
boundary2 = b2{k2};
plot(boundary2(:,2), boundary2(:,1), 'g', 'LineWidth', 1)
x2 = [x2; boundary2(:,2)];
y2 = [y2; boundary2(:,1)];
end
2 comentarios
Mathieu NOE
el 3 de Mayo de 2023
hello
it would help if you could share b1 and b2 as mat file
how do you want to reduce the amount of data if you keep step size ??
Respuesta aceptada
Mathieu NOE
el 3 de Mayo de 2023
hello again
I could reduce the amount of data by a factor 3 roughly ,
more could be done if the large "straigth" lines did not include some local kincks
Code suggestion :
load('example.mat');
x1=[];
y1=[];
x2=[];
y2=[];
c_threshold = 0.5; % curvature threshold parameter
figure(1)
for k1 = 1:length(b1)
boundary1 = b1{k1};
x = boundary1(:,2);
y = boundary1(:,1);
[k] = find_high_curvature(x,y,c_threshold);
x_out = x(k);
y_out = y(k);
plot(x, y, '*r', x_out, y_out, 'ob' ,'LineWidth', 2)
hold on
x1 = [x1; x_out];
y1 = [y1; y_out];
end
figure(2)
for k2 = 1:length(b2)
boundary2 = b2{k2};
x = boundary2(:,2);
y = boundary2(:,1);
[k] = find_high_curvature(x,y,c_threshold);
x_out = x(k);
y_out = y(k);
plot(x, y, '*r', x_out, y_out, 'ob' ,'LineWidth', 2)
hold on
x2 = [x2; x_out];
y2 = [y2; y_out];
end
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
function [highCurvatureIndexes] = find_high_curvature(x,y,threshold)
% Now run along the (x, y) curve
% and find the radius of curvature at each location.
numberOfPoints = length(x);
curvature = zeros(1, numberOfPoints);
for t = 1 : numberOfPoints
if t == 1
index1 = numberOfPoints;
index2 = t;
index3 = t + 1;
elseif t >= numberOfPoints
index1 = t-1;
index2 = t;
index3 = 1;
else
index1 = t-1;
index2 = t;
index3 = t + 1;
end
% Get the 3 points.
x1 = x(index1);
y1 = y(index1);
x2 = x(index2);
y2 = y(index2);
x3 = x(index3);
y3 = y(index3);
% Now call Roger's formula:
% http://www.mathworks.com/matlabcentral/answers/57194#answer_69185
curvature(t) = 2*abs((x2-x1).*(y3-y1)-(x3-x1).*(y2-y1)) ./ ...
sqrt(((x2-x1).^2+(y2-y1).^2)*((x3-x1).^2+(y3-y1).^2)*((x3-x2).^2+(y3-y2).^2));
end
% Find high curvature points -
% indexes where the curvature is greater than threshold
highCurvatureIndexes = find(curvature > threshold);
end
14 comentarios
Mathieu NOE
el 9 de Mayo de 2023
tried something different , like downsampling your data close enough to the target points
it's simply picking very n points and defining the decimation factor so that the total qty is close as posible to the given N value
this is a different approach that has no more anything to do with my initial curvature computation
tic
clc
clearvars
load('example.mat');
x1=[];
y1=[];
x2=[];
y2=[];
N = 200; % approx total number of points
for k1 = 1:length(b1)
boundary1 = b1{k1};
x1 = [x1; boundary1(:,2)];
y1 = [y1; boundary1(:,1)];
end
for k2 = 1:length(b2)
boundary2 = b2{k2};
x2 = [x2; boundary2(:,2)];
y2 = [y2; boundary2(:,1)];
end
figure(1)
subplot(1,2,1),plot(x1, y1, '*r', x2, y2, '*b','LineWidth', 1)
title('before resizing')
nx = numel(x1);
if nx>N % pick 1 every decim points
decim = ceil(nx/N);
ind = 1:decim:nx;
x1 = x1(ind);
y1 = y1(ind);
end
nx = numel(x2);
if nx>N % pick 1 every decim points
decim = ceil(nx/N);
ind = 1:decim:nx;
x2 = x2(ind);
y2 = y2(ind);
end
subplot(1,2,2),plot(x1, y1, '*r', x2, y2, '*b','LineWidth', 1)
title('after resizing')
%% Distance computations
% Distance x
% % original code (slow, only distancex alone needs +30 seconds to complete)
% distancex=[];
% for lenx1=1:length(x1)
% for lenx2=1:length(x2)
% distancex=[distancex x2(lenx2)-x1(lenx1)];
% end
% end
% prealocate data for faster execution (Elapsed time is 0.020392 seconds!!)
distancex=zeros(1,n1*n2);
k = 0;
for lenx1=1:n1
for lenx2=1:n2
k = k+1;
distancex(k)= x2(lenx2)-x1(lenx1);
end
end
% % another alternative code (suggestion up to you to try)
% % Elapsed time is 0.014494 seconds.
% distX = x2'-x1;
% distX = reshape(distX',1,[]); % convert 2D array to col vector
% diff = sum(abs(distancex-distX)) % diff = 0 !! distX and distancex are equal
% % Distance y
% for leny1=1:length(y1)
% for leny2=1:length(y2)
% distancey=[distancey y2(leny2)-y1(leny1)];
% end
% end
% prealocate data for faster execution (Elapsed time is 0.020392 seconds!!)
distancey=zeros(1,n1*n2);
k = 0;
for leny1=1:n1
for leny2=1:n2
k = k+1;
distancey(k)= y2(leny2)-y1(leny1);
end
end
% original code (slow)
% for i=1:n1*n2
% distance=[distance ( distancex(i)^2 + distancey(i)^2 )^0.5 ];
% end
% much faster and in one line :
distance = sqrt(distancex.^2 + distancey.^2);
%-----------------------Comparaison des valeurs des distances------------
% original code (slow)
% for a=1:length(x1):length(distance)
% Les_distances_min=[Les_distances_min min(distance(a:a+length(x1)-1))];
%
% end
% much faster
ind = 1:n1:n1*n2;
Les_distances_min=zeros(1,numel(ind));% prealocate data for faster execution
for k=1:numel(ind)
a = ind(k);
Les_distances_min(k)= min(distance(a:a+n1-1));
end
toc
Más respuestas (0)
Ver también
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!