How to smooth surf?

238 visualizaciones (últimos 30 días)
Alexandra Roxana
Alexandra Roxana el 30 de Oct. de 2022
Comentada: Lorenzo Melito el 3 de En. de 2024
I'm having a surface plot with many spikes. I was wondering what I can do to smooth it. interp2 might be a solution, I guess, but I'm having problems with the dimensions. Here is a part of the program:
a=0;
b=2;
c=0;
d=4;
M=40;
N=60;
hx=(b-a)/(M+1);
hy=(d-c)/(N+1);
alpha=inv(A)*L;
sol=zeros((M+2),(N+2));
for k=1:N*M
i=rem(k,M);
if i==0
i=M;
end
j=(k-i)/M+1;
newsol(i,j)=alpha(k);
end
sol(2:M+1,2:N+1)=newsol;
[X,Y]=meshgrid(a:hx:b,c:hy:d);
C = 1 + (X <= 0.25 | X >= 1.75);
surf(X,Y,sol',C);
colormap([1 0 0; 0 0 1]);
hold on
plot(0,0,'ko','MarkerSize',10,'MarkerFaceColor','black')
text(0,0,'(0,0)','Fontsize',20,'Color','k', 'Horiz','left','Vert','top')
plot(2,0,'k>','MarkerSize',10,'MarkerFaceColor','black')
text(2,0,'x_1','Fontsize',20,'Color','k', 'Horiz','left','Vert','top')
plot(0,4,'k<','MarkerSize',10,'MarkerFaceColor','black')
text(0,4,'x_2','Fontsize',20,'Color','k', 'Horiz','left','Vert','top')
xlabel('cm')
ylabel('cm')
zlabel('longitudinal fluid velocity (cm/s)')
  2 comentarios
KALYAN ACHARJYA
KALYAN ACHARJYA el 30 de Oct. de 2022
A not defined?
Alexandra Roxana
Alexandra Roxana el 30 de Oct. de 2022
Editada: Alexandra Roxana el 30 de Oct. de 2022
I wouldn't want to post the entire program, I put these parts of the program for the dimensions. I can post an image though:

Iniciar sesión para comentar.

Respuestas (1)

John D'Errico
John D'Errico el 30 de Oct. de 2022
Editada: John D'Errico el 30 de Oct. de 2022
interp2 does NO smoothing. It is NOT designed to smooth anything, and would NOT be appropriate, because interpolation does not change any of your data.
And all you post is code that nobody can execute. So helping you is difficult. If you really want help, then make it easy to get help. All we see is a picture, with no data provided.
The simplest way to perform a 2-dimensional smoothing operation in MATLAB is to use conv2. But you need to be careful around the edges, so there is a fix. Since you provide no data at all, I'll make something up.
[X,Y] = meshgrid(1:100);
Z = sin((2*X-3*Y)/75) + randn(size(X))/10;
surf(Z)
As I said, the simple idea is to use a convolution in 2-d, with a Gaussian smoothing kernel. That will blur out the noise, and if the noise is random, then a blur will be good, as long as the signal in your surface is slowly varying. But you need to consider what happens at the edges. conv2 will effectively insert zeros outside of the array. And that will cause a bias in the results around the borders.
[xk,yk] = meshgrid(-5:5);
K = exp(-(xk.^2 + yk.^2)/10); K = K/sum(K(:));
surf(K)
The smoothing kernel I'll use is a simple truncated 2-d Gaussian shape, then rescaled to sum to 1. The size of that smoothing kernel is a factor, since a larger (wider) kernel would do more smoothing.
Now we can use this to perform a blurring smooth in the array Z. But if I just use conv2 directly with that kernel, maintining the same size array. we have a problem.
Zhat1 = conv2(Z,K,'same');
surf(Zhat1)
As you can see, there is a band around the edges that is clearly biased towards zero. We can fix that as I show below.
Zhat2 = conv2(Z,K,'same')./conv2(ones(size(Z)),K,'same');
surf(Zhat2)
As you can see, the result is much smoother now. Not perfect because the original array was pretty well contaminated with noise, but it is still smooth out to the edges of the array, with no biased band around the edge.
You can use other schemes of course, perhaps based on median filters. I could think of many ways. In fact, you could even download my own gridft from the file exchange, which can smooth very nicely.
  1 comentario
Lorenzo Melito
Lorenzo Melito el 3 de En. de 2024
@John D'Errico, fantastic answer! Thanks a lot for the very informative process description!

Iniciar sesión para comentar.

Etiquetas

Productos


Versión

R2017a

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by