Speeding up (vectorizing) barycentric interpolation
Ältere Kommentare anzeigen
Dear All, I have the following problem:
is it possible to speed up the barycentric interpolation given below? I presume that vectorization could be particularly effective but I do not know how to do it. As the code has to be run many times (and the size of matrices involved is rather large) any increase in efficiency would be helpful. Could GPU computing, after vectorization, be of any help here?
na = 100;
nh = 100;
nm = 100;
nap = na+2;
nhp = nh+2;
H = randn(nap,nhp) ;
M = randn(nap,nhp) ;
MP = randn(nap,nhp) ;
ap_trial = NaN(nh,nm) ;
hp_trial = NaN(nh,nm) ;
mp_trial = NaN(nh,nm) ;
[h_grid,m_grid] = ndgrid(1:nh,1:nm);
[ap_grid,hp_grid] = ndgrid(1:nap,1:nhp);
tic
for r0 = 0:1
for r1 = 0:(nap-2)
for r2 = 0:(nhp-2) % loops picking up triangles constructed by adjacent points in matrices H and M
h1 = H(1+r1+r0,1+r2+r0);
h2 = H(1+r1,2+r2);
h3 = H(2+r1,1+r2);
m1 = M(1+r1+r0,1+r2+r0);
m2 = M(1+r1,2+r2);
m3 = M(2+r1,1+r2);
% barycentric interpolation (weights)
w1 = ( (m2-m3)*( h_grid -h3) + (h3-h2)*( m_grid -m3) ) / ( (m2-m3)*(h1-h3) + (h3-h2)*(m1-m3) );
w2 = ( (m3-m1)*( h_grid -h3) + (h1-h3)*( m_grid -m3) ) / ( (m2-m3)*(h1-h3) + (h3-h2)*(m1-m3) );
w3 = 1 - w1 - w2;
% preventing extrapolation
w1(w1 < 0) = NaN;
w2(w2 < 0) = NaN;
w3(w3 < 0) = NaN;
% barycentric interpolation (results)
ap = w1 * ap_grid(1+r1+r0,1+r2+r0) + w2 * ap_grid(1+r1,2+r2) + w3 * ap_grid(2+r1,1+r2);
hp = w1 * hp_grid(1+r1+r0,1+r2+r0) + w2 * hp_grid(1+r1,2+r2) + w3 * hp_grid(2+r1,1+r2);
mp = w1 * MP(1+r1+r0,1+r2+r0) + w2 * MP(1+r1,2+r2) + w3 * MP(2+r1,1+r2);
ap_trial( isnan(ap) == 0 ) = ap( isnan(ap) == 0 );
hp_trial( isnan(hp) == 0 ) = hp( isnan(hp) == 0 );
mp_trial( isnan(mp) == 0 ) = mp( isnan(mp) == 0 );
end
end
end
toc
14 Kommentare
per isakson
am 5 Apr. 2020
Adam Pigon
am 5 Apr. 2020
per isakson
am 5 Apr. 2020
Bearbeitet: per isakson
am 6 Apr. 2020
The tic toc made me ask.
I cannot see how to vectorize any part of your code. (But other might.)

It helps a tiny bit to replace isnan(ap) == 0 by ~isnan(ap), etc
These six red lines takes more than 80% of the time (on my system).
darova
am 6 Apr. 2020
I added imagesc inside first for loop

Only a few elements is re-calculated all the time. Can you attach original data?
Adam Pigon
am 6 Apr. 2020
darova
am 6 Apr. 2020
On the animation matrix is hp_trial. I mean if you know that only a few elements (positions) re-calculated all the time you don't need these operations. Every cycle you are searching for NaN values (runs through entire matrix)
ap_trial( isnan(ap) == 0 ) = ap( isnan(ap) == 0 );
hp_trial( isnan(hp) == 0 ) = hp( isnan(hp) == 0 );
mp_trial( isnan(mp) == 0 ) = mp( isnan(mp) == 0 );
Maybe can be replaced with
ap1 = ap(1:5,1:5);
aptr1 = ap_trial(1:5,1:5);
aptr1( ~isnan(ap1) ) = ap1( ~isnan(ap1) ); % search only in up left corner
ap_trial(1:5,1:5) = aptr1;
- Original data will not help much I guess?
We will find out
Adam Pigon
am 8 Apr. 2020
darova
am 8 Apr. 2020
I tried to scale rand numbers by 15

Is this correct?

Adam Pigon
am 8 Apr. 2020
darova
am 8 Apr. 2020
Ok i understood. What about these? Those a values inside triangle too?
w1(w1 < 0) = NaN;
w2(w2 < 0) = NaN;
w3(w3 < 0) = NaN;
Adam Pigon
am 8 Apr. 2020
darova
am 8 Apr. 2020
Then you can use my brilliant idea again and search for NaN in triangle region

Adam Pigon
am 12 Apr. 2020
darova
am 12 Apr. 2020
Thanks for the link
Antworten (0)
Kategorien
Mehr zu Logical finden Sie in Hilfe-Center und File Exchange
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!