Summation of matrices using symsum or other

1 Ansicht (letzte 30 Tage)
Johan Burger
Johan Burger am 9 Dez. 2020
Kommentiert: Johan Burger am 10 Dez. 2020
I am trying to run a Monte Carlo simulation at about 1-10k iterations (N). Some of the inputs remain constant throughout the computation, while others (8 variables) are randomised at each iteration. My code currently works as follows:
  1. An array is created for each variable, with the length set to N.
  2. Each variable is passed through a function, which describes a mathematical equation.
  3. Data samples are analysed for trends.
In the past I have been using a for-loop and the symsum function but as N grows, the computation becomes very slow. Symsum requires a scalar for its bounds (but these are also arrays. One component of the final calculation is described by:
Where X, B and K are arrays. The symsum function I have been using is:
ans = double(symsum((X*Y)./((1+Z).^(A+k*B)),k,1,K));
I have played around with arrayfun, but the result was a single value instead of an array, size N, which I need.
My question is, how can I best calculate this value? I would need to run several of these simulations for my project and would like to trim down the time.
  2 Kommentare
Alan Stevens
Alan Stevens am 9 Dez. 2020
  1. Do you need to use the symbolic calculations at all, rather than purely numerical calculations?
  2. Can you share your whole code?
Johan Burger
Johan Burger am 9 Dez. 2020
  1. I don't have a requirement to use symbolic calculations. It was just the first option that came up when I initially wrote the code. So long as the end result is the same it doesn't matter. I would prefer to be able to vectorise the entire calculation, I suspect that the for-loop is why my simulation requires 60min for 10k runs.
  2. Here is the main for-loop for my project. The loop calculates the values for "repSum", "ic", etc. in each run and the final value, "lcos", is then analysed.
for i = 1:numberOfRuns
repSum(i) = double(symsum((cREP(i)*capP)/((1+r)^(tC+k*tR)),k,1,R(i)));
ic(i) = icPre(i) + repSum(i);
om_sum(i) = double(symsum((cPom(i)*capP + cEom(i)*...
(cycPa*DoD*capE)*(1-cycDeg)^((k-1)*cycPa)*(1-tDeg)^(k-1))/(1+r)^(k+tC),k,1,N(i)));
elec_sum = double(cycPa*DoD*capE*nRT*(1-nSELF)*symsum(((1-cycDeg)...
^((k-1)*cycPa)*(1-tDeg)^(k-1))/(1+r)^(k+tC),k,1,N));
eol_sum(i) = (icPre(i))*fEOL/(1+r)^(N(i)+1);
end
charge_sum = pEl/nRT*elec_sum;
lcos = (ic + om_sum + charge_sum + eol_sum)./elec_sum; %final value of interest.

Melden Sie sich an, um zu kommentieren.

Akzeptierte Antwort

Alan Stevens
Alan Stevens am 10 Dez. 2020
It's difficult to tell from what you've listed, but have you tried getting rid of all symbolic stuff and using just numerics (which are much faster)? For example:
for i = 1:numberOfRuns
repSum(i) = sum(cREP(i)*capP./(1+r)^(tC+k*tR));
ic(i) = icPre(i) + repSum(i);
om_sum(i) = sum((cPom(i)*capP + cEom(i)*...
(cycPa*DoD*capE)*(1-cycDeg)^((k-1)*cycPa)*(1-tDeg)^(k-1))/(1+r)^(k+tC),k,1,N(i));
elec_sum = cycPa*DoD*capE*nRT*(1-nSELF)*sum(((1-cycDeg)...
^((k-1)*cycPa)*(1-tDeg)^(k-1))/(1+r)^(k+tC),k,1,N);
eol_sum(i) = (icPre(i))*fEOL/(1+r)^(N(i)+1);
end
Although I can't tell where you might need to replace * by .* or ^ by .^ etc because of the limited information here.
Also, do you need to keep every value of repSum (you have repSum(i)) even though it doesn't seem to be used outside of the loop?
  1 Kommentar
Johan Burger
Johan Burger am 10 Dez. 2020
Thank you for your suggestion. What I was having trouble with was that "k" is also a vector that changes in each run but I think I have figured it out.

Melden Sie sich an, um zu kommentieren.

Weitere Antworten (0)

Kategorien

Mehr zu Cardiology finden Sie in Help Center und File Exchange

Produkte


Version

R2020b

Community Treasure Hunt

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

Start Hunting!

Translated by