Help on code optimization

조회 수: 2 (최근 30일)
Kostas
Kostas 2011년 12월 6일
I have two matrices A (519840x5) and B (319966x5). Columns 2 to 4 for both contain "day of the year (format: 1-366) ", "hour (format:0-23) " and "minute (format: 0-59)". I would like for each day, hour and minute of matrix B to get a value for the same day, hour and minute, from matrix A and insert it in A, in case they don't have a common day-hour-minute then this value to be -999. I have done using the following code, but since it is too slow i would appreciate any help for speed optimization
for i=1:size(B,1)
id=find(A(:,2)==B(i,2)&A(:,3)==B(i,3)&A(:,4)==B(i,4));
if size(id,1)==1 %check if condition exists
tot=A(id,5); % if yes then get this value
else
tot=-999; %otherwise tot=-999
end
B(i,6)=tot; %insert to last comlum the tot value
end
Thank you

채택된 답변

Walter Roberson
Walter Roberson 2011년 12월 6일
Unfortunately I do not have access at the moment to test this:
[uAkey, mA, nA] = unique(A(:,2)*10000 + A(:,3)*100 + A(:,4));
[uBkey, mB, nB] = unique(B(:,2)*10000 + B(:,3)*100 + B(:,4));
[tf, idx] = ismember(uvB, uvA);
B(~tf,6) = -999; %the ones not found
B(tf,6) = A(mA(idx(tf)),5);
Yes, this is a bit tricky in the name of efficiency.
A less tricky and less efficient version would be:
Akey = A(:,2)*10000 + A(:,3)*100 + A(:,4);
Bkey = B(:,2)*10000 + B(:,3)*100 + B(:,4);
[tf, idx] = ismember(Bkey, Akey);
B(~tf,6) = -999;
B(tf,6) = A(idx,5);
In either case, if there are duplicate B then they will all be assigned the same value. If there are duplicate A keys, both versions of the code will use the id from the last entry in A with that key.
  댓글 수: 1
Kostas
Kostas 2011년 12월 6일
To be total honest i am still trying to understand how your code works, but it 's really great, it did what i wanted in just few seconds while in my way it took almost 20 minutes. Thanks a lot

댓글을 달려면 로그인하십시오.

추가 답변 (1개)

bym
bym 2011년 12월 6일
you might start by pre-allocating the new size of B before the for loop:
B = [B,zeros(319955,1)];
for i = 1:length(B)
id=find(A(:,2)==B(i,2)&A(:,3)==B(i,3)&A(:,4)==B(i,4));
if size(id,1)==1 %check if condition exists
tot=A(id,5); % if yes then get this value
else
tot=-999; %otherwise tot=-999
end
B(i,6)=tot; %insert to last comlum the tot value
end
  댓글 수: 1
Walter Roberson
Walter Roberson 2011년 12월 6일
pre-allocating is not really relevant here. If the 6th column does not exist then the first assignment to that column will create the entire column (all rows); in very new versions it might even be able to the extension in-place.

댓글을 달려면 로그인하십시오.

카테고리

Help CenterFile Exchange에서 Operators and Elementary Operations에 대해 자세히 알아보기

Community Treasure Hunt

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

Start Hunting!

Translated by