nonlinear regression for multiple variable parameter

9 次查看(过去 30 天)
I'm trying to write code to perform a nonlinear regression with multiple variables, but i have no idea how to do it.
i need to use Keq and pressure like Xdata and define the x1,x2,x3 from the regression.
I hope I have explained myself.
Function value and YDATA sizes are not equal.
Error in prova3 (line 49)
x_fit = lsqcurvefit(T, x0, [pressure Keq], temperature);
clc
clear all
close all
%%
%read all .xlsx file inside the folder
path = dir('C:\Users\Andrea\Desktop\matlab\input_file\*.xlsx');
%cicle for obtain the sample data (P-T-Ni) content directly from the .xlsx file
for i=1:1
table = readtable(strcat('C:\Users\Andrea\Desktop\matlab\input_file\',path(i).name));
temperature(:,i) = table.temperature;
pressure(:,i) = table.pressure;
Ni_grt(:,i) = table.Ni_Grt;
Ni_ol(:,i) = table.Ni_Ol;
Cr_grt(:,i) = table.Wt_Cr;
Ca_grt(:,i) = table.Wt_Ca;
end
%% calculation
%Keq
Ni_grt = Ni_grt(~isnan(Ni_grt), :);
Keq= log(Ni_grt/2900);
%temperature from C to K
temperature = temperature + 273.15;
%olivine mean
Ni_ol = Ni_ol(~isnan(Ni_ol), :);
mean_Ni_ol = mean(Ni_ol);
%% ignore the NaN value
temperature = temperature(~isnan(temperature), :);
pressure = pressure(~isnan(pressure), :);
Ca_grt = Ca_grt(~isnan(Ca_grt), :);
Cr_grt = Cr_grt(~isnan(Cr_grt), :);
%% Calculate the parameters (ΔH, ΔV, ΔS)
% function of T
T = @(x,pressure,Keq) (x(1) + pressure * x(2)) ./ (x(3) - log(Keq));
% random start parameters (ΔH, ΔV, ΔS)
x0 = [1, 1, 1];
% nonlinear regression with lsqcurvefit
x_fit = lsqcurvefit(T, x0, [pressure Keq], temperature);
% Extract the fitted parameters
DeltaH = x_fit(1);
DeltaV = x_fit(2);
DeltaS = x_fit(3);
% the new value od temperature from Ni_grt of database
predicted_temperature = T(x_fit, pressure);
% print the result
fprintf('Parametri adattati:\n');
fprintf('ΔH = %.2f\n', DeltaH);
fprintf('ΔV = %.2f\n', DeltaV);
fprintf('ΔS = %.2f\n', DeltaS);
fprintf('Ni_ol = %.2f\n', mean_Ni_ol);
%% diff TNi-T
deltaT = predicted_temperature-temperature;
mean_deltaT = mean(deltaT);
fprintf('mean_detaT = %.2f\n', mean_deltaT);

采纳的回答

Star Strider
Star Strider 2023-9-27
Your code works. The only change required was to create the ‘pressure_Keq’ matrix as the independent variable and then change ‘T’ to refer to it correctly internally.
Try this —
clc
clear all
close all
%%
%read all .xlsx file inside the folder
% path = dir('C:\Users\Andrea\Desktop\matlab\input_file\*.xlsx');
path = dir('*.xlsx');
%cicle for obtain the sample data (P-T-Ni) content directly from the .xlsx file
for i=1:1
% table = readtable(strcat('C:\Users\Andrea\Desktop\matlab\input_file\',path(i).name));
table = readtable(path(i).name)
temperature(:,i) = table.temperature;
pressure(:,i) = table.pressure;
Ni_grt(:,i) = table.Ni_Grt;
Ni_ol(:,i) = table.Ni_Ol;
Cr_grt(:,i) = table.Wt_Cr;
Ca_grt(:,i) = table.Wt_Ca;
end
table = 171×6 table
pressure temperature Ni_Grt Wt_Cr Wt_Ca Ni_Ol ________ ___________ ______ ______ ______ _____ 61.627 1292.9 119.99 9.5358 6.7344 NaN 59.458 1280 91.07 4.7708 5.4524 3858 59.035 1269.2 199.38 11.087 6.926 NaN 57.332 1198.3 51.712 11.273 6.2995 3078 58.42 1266.4 84.844 5.8212 5.8972 3110 66.891 1265.2 74.004 2.0122 4.1251 3734 62.266 1276 114.78 4.7802 5.1415 NaN 63.981 1223.7 79.805 9.2159 6.561 NaN 66.462 1284.9 109.54 2.6306 4.3678 3650 68.121 1315 104.8 2.6699 4.372 NaN 60.293 1291.5 143.75 9.6895 6.3098 NaN 48.298 911.33 25.03 6.5673 6.485 NaN 39.735 889.06 138.1 7.4448 7.0952 NaN 29.302 761.53 19.58 5.1597 6.3017 NaN 48.895 894.94 28.51 5.4462 5.466 NaN 59.131 987.97 35.22 6.7152 6.3878 NaN
%% calculation
%Keq
Ni_grt = Ni_grt(~isnan(Ni_grt), :);
Keq= log(Ni_grt/2900);
%temperature from C to K
temperature = temperature + 273.15;
%olivine mean
Ni_ol = Ni_ol(~isnan(Ni_ol), :);
mean_Ni_ol = mean(Ni_ol);
%% ignore the NaN value
temperature = temperature(~isnan(temperature), :);
pressure = pressure(~isnan(pressure), :);
Ca_grt = Ca_grt(~isnan(Ca_grt), :);
Cr_grt = Cr_grt(~isnan(Cr_grt), :);
%% Calculate the parameters (ΔH, ΔV, ΔS)
% function of T
pressure_Keq = [pressure Keq]; % Create The Independent Variable As A Matrix, Then Address Its Columns Appropriately In The Objective Function
T = @(x,pressure_Keq) (x(1) + pressure_Keq(:,1) * x(2)) ./ (x(3) - log(pressure_Keq(:,2)));
% random start parameters (ΔH, ΔV, ΔS)
x0 = [1, 1, 1];
% nonlinear regression with lsqcurvefit
x_fit = lsqcurvefit(T, x0, pressure_Keq, temperature);
Local minimum possible. lsqcurvefit stopped because the final change in the sum of squares relative to its initial value is less than the value of the function tolerance.
% Extract the fitted parameters
DeltaH = x_fit(1);
DeltaV = x_fit(2);
DeltaS = x_fit(3);
% the new value od temperature from Ni_grt of database
predicted_temperature = T(x_fit, pressure_Keq);
% print the result
fprintf('Parametri adattati:\n');
Parametri adattati:
fprintf('ΔH = %.2f\n', DeltaH);
ΔH = -2319.97
fprintf('ΔV = %.2f\n', DeltaV);
ΔV = -9.90
fprintf('ΔS = %.2f\n', DeltaS);
ΔS = -0.67
fprintf('Ni_ol = %.2f\n', mean_Ni_ol);
Ni_ol = 2759.78
%% diff TNi-T
deltaT = predicted_temperature-temperature;
mean_deltaT = mean(deltaT);
fprintf('mean_detaT = %.2f\n', mean_deltaT);
mean_detaT = 0.34
.
  2 个评论
andrea rigotto
andrea rigotto 2023-9-28
编辑:andrea rigotto 2023-9-28
thank you for reply, but the results are in complex numbers, how can I obtain the results in real numbers?
Star Strider
Star Strider 2023-9-28
That may be because you are calculating the logarithm of a negative number.
I just noticed this now, that these two calculations appear to be redundant:
Keq = log(Ni_grt/2900);
that division is likely to result in values less than 1 (so the log of ‘Keq’ will be negative in those instances), and later you take the log of ‘Keq’ in ‘T’:
T = @(x,pressure_Keq) (x(1) + pressure_Keq(:,1) * x(2)) ./ (x(3) - log(pressure_Keq(:,2)));
Perhaps taking the log of ‘Keq’ in ‘T’ needs to be changed, so that you are only subtracting ‘Keq’ and not the log of it.
I do not know what you are calculating, so I am hesitant to make any other changes to your code.
.

请先登录,再进行评论。

更多回答(0 个)

类别

Help CenterFile Exchange 中查找有关 Linear Regression 的更多信息

Community Treasure Hunt

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

Start Hunting!

Translated by