What else can I do to speed up evaluation of this function?

1 view (last 30 days)
I'm working with a function which is being called many times as part of a fitting algorithm. So I want to optimize it and reduce the runtime as much as possible. What more can I do for this? This i what I have already done:
  • truncated the numerical integration with an anonymous function so that I don't integrate over the entire thing;
  • reduced the relative tolerance for integration of the anonymous function;
  • wrote code using scientific notation (e.g. 1e5 instead of 10^5);
Edit: all the variables passed to the function are scalars, with the exception of abs_coeff and photon_flux, which are function handles, and V which is an 1-D array.
Right now the runtime for the function is between 0.9 - 15s, depending on the variables. Any optimization advice is welcome, thanks!
function j_sol = Reichman_ntype(In_0, Ip_0, N, n_i, tau, L, epsilon, phi_b0, T, abs_coeff, photon_flux, V)
q = 1.602176565e-19; % Elementary charge [C]
k_B = 1.38064852e-23; % m^2 * kg / s^2 / K
epsilon_0 = 8.8541878128e-14; %F/cm
p0 = n_i^2/N; %hole conc in /cm^3
J_n = -In_0/1000 * (exp(q * V/(k_B * T)) - 1); % electron current in mA/cm^2
phi_b = phi_b0 - V; %barrier in V
J_0 = 1000 * q * p0 * L / tau; %saturation current, units: mC * cm^-6/cm^-3 * cm/s = mA/cm^2
A = Ip_0 + J_0 * exp (q*V/(k_B * T)); %mA/cm^2
W = sqrt(2 * epsilon * epsilon_0 * phi_b / (q * N)); %depletion layer width, units: cm
K = pi * k_B * T * n_i * W .* exp(q * V / (2*k_B*T)) ./ (4 * tau * phi_b);
% units: J * cm^-3 * cm / (s * V) = mA/cm^2
j_sol = integral(@(x) ...
J_n + Ip_0 * ((((-K + (K.^2 + 4 * A .* (Ip_0 + (J_0 + 1e3 * q * photon_flux(x) *...
(1 - exp(-abs_coeff(x)*1e7 .* W)/(1 + abs_coeff(x)*1e7 * L))))).^(1/2))./(2 * A)).^2) -1), ...
250 , 1500, 'ArrayValued', true, 'RelTol', 0.01, 'AbsTol', 0); %mA/cm^2
end
P.S. Parallelization is not an option since this function is being called in a parfor already.

Accepted Answer

Jon
Jon on 29 Sep 2020
You can get determine where you are spending time using MATLAB's profiler https://www.mathworks.com/help/matlab/matlab_prog/profiling-for-improving-performance.html
Also can you include the code for photon_flux, and abs_coeff, maybe the inefficiencies are there
  2 Comments
Radu Bors
Radu Bors on 29 Sep 2020
Hi, thanks for the profiler idea, I’ll give it a try and update the post.
abs_coeff and photon_flux are anonymous functions which interpolate some x-y data using interp1. I followed this approach because the abs_coeff and photon_flux were different sizes and didn’t have y data at matching x values. But now that you mention it, they may be the reason for the long computation time. I’ll check with profiler.
Thanks for the great suggestions again!
Radu Bors
Radu Bors on 30 Sep 2020
Hey, you were right. Out of 15s runtime (using weaker CPU this time), 9 seconds are spent calling the interp1 function when using abs_coeff and photon_flux. I'll see what to do about that. Thanks for the guidance!

Sign in to comment.

More Answers (0)

Products


Release

R2020b

Community Treasure Hunt

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

Start Hunting!