how to delete nan values from array columns without losing data from other columns
3 次查看(过去 30 天)
显示 更早的评论
i have a huge file from a lab expremient
every run gives me 4 columns and every 2 out of the 4 start with nan then 2 nan vars and end with nan and 3 nan vars i want to delet the nan values without losing any data so that when i try to make graphs from it every graph will have enough inputs and neither of them get lost
i am espisally troubled by the second 2 columns of every 4 and how to deal with them
11 个评论
Mathieu NOE
2024-5-14
glad I could help a bit , but this was just a starter
ok, let's focus on the selected runs (for both files I presume ?)
these 2 lines are indeed just to extract a block of 4 contiguous columns , and we simply shift by a factor 4 when we change to the next run :
ind_cols = (1:4)+(ck-1)*4;
data_this_run = data(:,ind_cols);
and yes this line is not anymore of any use (I used it for another purpose that I removed afterwards) : [m,n] = size(data_this_run);
I'll come back soon with a new code
采纳的回答
Mathieu NOE
2024-5-14
ok, so this is now the main dishes....
have first tried this code on the first data file , will adapt to your new files as soon as possible
have fun !
data= readmatrix('expr2lab.csv'); % or readtable or whatever
runs = [12 , 16 ,17,20,22,24,29,30,31,34,33,11]; % selection of best runs
%% main loop
for ck = 1:numel(runs)
k = runs(ck);
ind_cols = (1:4)+(k-1)*4; % Time (s) Position (m) Velocity (m/s) Acceleration (m/s²)
data_this_run = data(:,ind_cols);
[m,n] = size(data_this_run);
Time = data_this_run(:,1);
Position = data_this_run(:,2);
Velocity = data_this_run(:,3);
Acceleration = data_this_run(:,4);
%% fit on acceleration data
% remove all NaN's first
ind = isnan(Time) | isnan(Acceleration);
Time(ind) = [];
Position(ind) = [];
Velocity(ind) = [];
Acceleration(ind) = [];
% select valid data between first max peak and end of data
[v,indm] = max(Acceleration); % search for the first positive max peak
nn = numel(Time);
[b,yf] = exp_decay_sinus_fit(Time(indm:nn),Acceleration(indm:nn));
% b array contains 5 coefficients according to this equation (model)
% y = b(1).*exp(b(2).*x).*(sin(2*pi*b(3)*x + b(4))) + b(5)
eq_str = [ ' y = ' num2str(b(1),'%.2f'),'* exp(-' num2str(-b(2),'%.2f') ' t * sin(2*pi*' num2str(b(3),'%.2f') ' t + ' num2str(b(4),'%.2f') ' ) + (' num2str(b(5),'%.2f') ')'];
figure(ck)
subplot(3,1,1),plot(Time,Position)
title(['Run # : ' num2str(k)]);
ylabel('Position');
subplot(3,1,2),plot(Time,Velocity)
ylabel('Velocity');
subplot(3,1,3),plot(Time,Acceleration,Time(indm:nn),yf);
ylabel('Acceleration');
legend('data',eq_str);
end
%%%%%%%%%%%%%%% functions %%%%%%%%%%%%%%%%%%%%%%
function [B,yf] = exp_decay_sinus_fit(t,y)
[yu,indm] = max(y);
yl = min(y);
yr = (yu-yl); % Range of y
yz = y-yu+(yr/2);
% zero crossing are performed on first 1/3 of data (better signal to
% noise ratio)
n = round(numel(y)/3);
yz = yz(indm:n); % extract from first major peak to end of 30% of data
zt = t(yz(:) .* circshift(yz(:),[1 0]) <= 0); % Find zero-crossings
per = 2*mean(diff(zt)); % Estimate period
freq = 1/per; % Estimate frequency
% initial phase estimate
tmax = t(indm);
phase_init = mod(-2*pi*freq*tmax + pi/2,2*pi); % initial phase estimate
ym = mean(y); % Estimate DC value (offset)
fit = @(b,x) b(1).*exp(b(2).*x).*(sin(2*pi*b(3)*x + b(4))) + b(5); % Objective Function to fit
fcn = @(b) norm(fit(b,t) - y); % Least-Squares cost function
B = fminsearch(fcn, [yr; -0.1; freq; phase_init; ym]); % Minimise Least-Squares
if B(4)<0 % complement negative phase with 2pi
B(4) = B(4) + 2*pi;
end
yf = fit(B,t);
end
4 个评论
更多回答(0 个)
另请参阅
类别
在 Help Center 和 File Exchange 中查找有关 Get Started with Curve Fitting Toolbox 的更多信息
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!