Info

此问题已关闭。 请重新打开它进行编辑或回答。

Any tips on how I can vectorize my code?

1 次查看(过去 30 天)
Cathleen Turner
Cathleen Turner 2013-5-31
关闭: MATLAB Answer Bot 2021-8-20
Hi all, I would really appreciate some tips on how I vectorize my simple code. Essentially I am taking data from a data structure I made and creating a cleaner and simpler structure (to keep the previous one relatively unaltered, for record purposes). Essentially I am taking data from a structure (of raw data) and putting it into a "nice" structure that is sorted and has more intuitive headers. It would make the data work with for more people.
For each parameter (temperature, salinity) there is a site name, date, time, and month. In the excel file there is a column with the site name and month (someone made it) so I change the string to double and separated the sites using the numbered name. For example: sitename.parameter....(GSO.temp) and the temperature will be a cell, each cell for a month (if you have 9 months you have 9 cells)
So now I am at the point where I use forloops to create the structure and cells so that you can take any size data (even if it is missing a month or certain cours) to do this. So far I have nested for loops for every parameter (temperature, salinity) but me no like! My final goal is to make it into a function for making many plots and you can specify what parameter you want to work with, but I might do a separate function for that. How can I improve my code?
I only show temperature because I would do the same for the other parameters hehe
%This is to make a single plot out of a dataset
%site name should be in double (as in a vector), for easy sorting-use
%time should be in string- use Sample_Date_and_Time
%data can be a vector or structure, whatever
%it should take the string of the datastructure header and use it to title
%the plot
%This
%if 1-seperate by site name
%if 2-seperate by month
%para is to specify the parameter you wish to have a plot of
%ALL PARAMETERS==0
%Temperature (deg C)==1
%Salinity psu ==2
%Alkalinity (mol/kg)==3
%measured DIC (mol/kg)==4
%pH==5
%Kc==6
%Ka==7
%Flux==8
%Tc==9
%pCO2 (aq)==10
sortby=input.site_month_vector;
sort=zeros(length(sortby),1);
%obtain times
times=input.Sample_Date_and_Time;
for i=1:length(sortby)
%Sort each paramter by site name
%Temperature (deg C)
if (para==0 || para==1) %if para=0 do this, or is para=1 do this...will not bother to look at second statement is first is true!
Tempdata=[input.site_month_vector input.date_num input.Measured_In0x2Dsitu_Temp__C];
%To have a year of continuous data separated by site
Temp=cell(length(Tempdata),3); %one for every month
Temp{1}=Tempdata(Tempdata(:,1)==71 & Tempdata(:,2)==83,:); %to sort out GSO
Temp{2}=Tempdata(Tempdata(:,1)==71 & Tempdata(:,2)==82,:); %to sort out GRW
Temp{3}=Tempdata(Tempdata(:,1)==80 & Tempdata(:,2)==67,:); %to sort out PC
%Option of having all the temperature in one vector, removing site
%and date tag (only datnum and temperature)
GSO.alltemp=Temp{1}(:,end-1:end);
GRW.alltemp=Temp{2}(:,end-1:end);
PC.alltemp=Temp{3}(:,end-1:end);
A=Temp{1};
B=Temp{2};
C=Temp{3};
A(:,1:3)=[]; %remove the letters of GSO
B(:,1:3)=[]; %remove the letters of GRW
C(:,1:3)=[]; %remove the letters of PC
%each month is represented by three letters, therefore the
%first 3 numbers, all sites will have the same name for months
%but not all data will have the same months
Sum1=A(:,1)+A(:,2)+A(:,3)+A(:,4);
Sum2=B(:,1)+B(:,2)+B(:,3)+B(:,4);
Sum3=C(:,1)+C(:,2)+C(:,3)+C(:,4);
%Remove month, replace with sum to use the sum as a tag
A(:,1:4)=[]; B(:,1:4)=[];C(:,1:4)=[];
A=[Sum1 A];B=[Sum2 B]; C=[Sum3 C];
%create a new structure of data of format sitename.parameter.
%This is is a clean version of data
GSO.Temp=cell(length(Tempdata),12);
GRW.Temp=cell(length(Tempdata),12);
PC.Temp=cell(length(Tempdata),12);
Monthtag1=unique(Sum1);
Monthtag2=unique(Sum2);
Monthtag3=unique(Sum3);
for i=1:length(Monthtag1)
GSO.Temp{i}=A(A(:,1)==Monthtag1(i),:);
end
for i=1:length(Monthtag2)
GRW.Temp{i}=B(B(:,1)==Monthtag2(i),:);
end
for i=1:length(Monthtag3)
PC.Temp{i}=C(C(:,1)==Monthtag3(i),:);
end
end
end
  1 个评论
Walter Roberson
Walter Roberson 2013-5-31
编辑:Walter Roberson 2013-5-31
Possibly using structfun() or arrayfun() could be used to make the code cleaner -- though not necessarily more efficient.
In situations such as this, struct2cell() is often useful.

回答(2 个)

Jan
Jan 2013-5-31
Not a vectorization, but a hint:
Letting an array shrink repeatedly requires time:
A = Temp{1};
A(:,1:3) = [];
Sum1 = A(:,1) + A(:,2) + A(:,3) + A(:,4);
A(:,1:4) = [];
A = [Sum1 A];
Most likely faster:
A = Temp{1};
Sum1 = A(:,4) + A(:,5) + A(:,6) + A(:,7);
A = [Sum1, A(:, 5:end)];
And the same for B and C.
Accessing a field of a struct requires time. So omit in loops when possible. Your code:
GSO.Temp = cell(length(Tempdata),12);
Monthtag1 = unique(Sum1);
for i = 1:length(Monthtag1)
GSO.Temp{i} = A(A(:,1)==Monthtag1(i),:);
end
And slightly faster:
GSO_Temp = cell(length(Tempdata),12);
Monthtag1 = unique(Sum1);
for i = 1:length(Monthtag1)
GSO_Temp{i} = A(A(:,1) == Monthtag1(i),:);
end
GSO.Temp = GSO_Temp;

Cathleen Turner
Cathleen Turner 2013-6-3
Thank you!

此问题已关闭。

产品

Community Treasure Hunt

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

Start Hunting!

Translated by