I recently learned of ParametricNDSolve and found that I need to compute it once and then call its result sol at different parameters x,y from rmat many times in the following example code. But always only evaluated at the same grid ttlist of the ODE time variable t, if this is relevant at all.
It turns out to be the bottleneck of my task. In reality I have much larger Ntt and Nr, so I need to speed it up as much as possible. (The form of eqs doesn't matter here.) Therefore I was wondering if any speed optimization possible? Either using Compile or not is fine.
Not sure if this is a stupid question as the result of ParametricNDSolve is probably not compilable. Just out of hope and curiosity...
eqs = {I Derivative[1][B1][t] == Abs[B1[t]]^2 (m B1[t] + B3[t] (x - I y + Cos[t] - I Sin[t])) +
Abs[B2[t]]^2 (m B1[t] + B3[t] (x - I y + Cos[t] - I Sin[t])) + (B1[t] Conjugate[B3[t]] + B2[t] Conjugate[B4[t]]) (-m B3[t] +
B1[t] (x + I y + Cos[t] + I Sin[t])),
I Derivative[1][B2][t] == Abs[B1[t]]^2 (m B2[t] + B4[t] (x - I y + Cos[t] - I Sin[t])) +
Abs[B2[t]]^2 (m B2[t] + B4[t] (x - I y + Cos[t] - I Sin[t])) + (B1[t] Conjugate[
B3[t]] + B2[t] Conjugate[B4[t]]) (-m B4[t] + B2[t] (x + I y + Cos[t] + I Sin[t])),
I Derivative[1][B3][t] == B1[t] (m (B3[t] Conjugate[B1[t]] +
B4[t] Conjugate[B2[t]]) + (Abs[B3[t]]^2 + Abs[B4[t]]^2) (x + I y + Cos[t] + I Sin[t])) +
B3[t] (-m (Abs[B3[t]]^2 + Abs[B4[t]]^2) + (B3[t] Conjugate[B1[t]] + B4[t] Conjugate[B2[t]]) (x + Cos[t] - I (y + Sin[t]))),
I Derivative[1][B4][t] == B2[t] (m (B3[t] Conjugate[B1[t]] +
B4[t] Conjugate[B2[t]]) + (Abs[B3[t]]^2 + Abs[B4[t]]^2) (x + I y + Cos[t] + I Sin[t])) +
B4[t] (-m (Abs[B3[t]]^2 + Abs[B4[t]]^2) + (B3[t] Conjugate[B1[t]] + B4[t] Conjugate[B2[t]]) (x + Cos[t] - I (y + Sin[t])))};
ic = {B1[-tmax] == 1, B2[-tmax] == 0, B3[-tmax] == 0, B4[-tmax] == 1};
var = {B1, B2, B3, B4};
tmax = 25; m = 0.4;
ttmax = tmax; ttmesh = ttmax/4; ttlist = Table[tt, {tt, -ttmax, ttmax, ttmesh}];
Ntt = Length@ttlist; Nr = 4;
rmat = RandomReal[1, {Nr, Nr, Ntt, Ntt, 2}];
sol = ParametricNDSolveValue[{eqs, ic}, Outer[#2[#] &, ttlist, var], {t, -tmax, tmax}, Element[#, Reals] & /@ {x, y}];
data = ParallelTable[
With[{rxy = rmat[[ix, iy]]},
Module[{Amat =
Table[Apply[sol, rxy[[it1, it2]]][[it1]], {it1, Ntt}, {it2, Ntt}]},
Total[Amat, 2](example of much faster computation that follows)]], {ix, Nr}, {iy, Nr}];
data // Abs // MinMax
ParametricFunction[](which is the head of whatParametricNDSolveValue[]returns) isn't in there. – J. M.'s missing motivation Feb 18 '21 at 13:08NttandNr, so I need to speed it up as much as possible. – xiaohuamao Feb 20 '21 at 02:26datalooks like{{1, 1, 1, 1}, {1, 1, 1, 1}, {1, 1, 1, 1}, {1, 1, 1, 1}}. How we can compare faster code with this one? – Alex Trounev Feb 20 '21 at 23:35AmatinsideModuleinsidedata. I need this and then some other computation that is much faster and hence I just put1as a placeholder. – xiaohuamao Feb 21 '21 at 02:30Amat, but you code is not optimized. Let suppose that we can do it 10-100 times faster. Then we can compare final result with yourdata, But yourdatanot shows any result dependent onAmat. Can you put some function instead of 1 so that we can comparedata. – Alex Trounev Feb 21 '21 at 11:21PrecisionGoal? BelowPrecisionGoal -> 5I run into trouble on the test code (error is too large). With a setting of5, I get 2-3 digits of precision in theMinMaxresult. It's only a modest savings of time (~40%). – Michael E2 Feb 21 '21 at 17:03