I'm still learning Mathematica, and I'm trying to write a program that needs to invert a large (nxn, n=160 or possibly larger than this) matrix with numerical entries, multiply with to another matrix, diagonalize the resulting matrix and then compute the n ipr (inverse participation ratio) values from its n eigenvectors. Because at the end of the program I also need to find some statistical quantities (mean,median, min, max) on these ipr values, I am using a Do loop to repeat the aforementioned matrix operations 100 times, so that I obtain a 100-dim list (each element is itself a list of n ipr values), and average over each column, which will give me a list of n average ipr values.
Here's the program:
n = 160; t = 100;
H = Table[0.0, {2 n}, {2 n}];
ipr[v_] := Sum[Abs[v[[i]]]^4, {i, Length[v]}];
iprv = Table[0.0, {i, t}];
Do[
Print[s];
m = Table[RandomReal[{0, 0.5}], n];
k = RandomReal[{0, \[Pi]}];
M = Table[If[i == j, 2, 1/(Abs[i - j])^3], {i, 1, n}, {j, 1, n}];
F = Inverse[M];
Print["y"];
Psi = Abs[F.m];
h1 = Table[If[i == j, (1 - Cos[k]) + Psi[[i]], Sqrt[Psi[[i]] Psi[[j]]]/(2*(Abs[i - j])^3)],
{i, 1, n}, {j, 1, n}];
h2 = Table[If[i == j, Psi[[i]], Sqrt[Psi[[i]] Psi[[j]]]/(2*(Abs[i - j])^3)], {i, 1, n}, {j,
1, n}];
H = ArrayFlatten[{{h1, h2}, {-h2, -h1}}];
{h, u} = Eigensystem[H]; v = Pick[u, NonNegative[h]];
iprv [[s]] = Table[ipr[v[[i]]], {i, Length[v]}],
{s, t}
]
mipr = Mean[iprv];
max = Max[mipr]
min = Min[mipr]
me = Mean[mipr]
med = Median[mipr]
stat = {me, med, min, max};
Print[stat];
The problem is that this program runs very slow on my computer (it takes approx 5 min to do each loop), and I believe the problem is the large matrix inversion. Do you have any experience on inverting large matrices on Mathematica and any suggestion on how to speed it up? Is there anything else in the Do loop that can be optimized (even the Do loop itself), that might be slowing down the program?
Thank you so much for the help!
M = Table[If[i == j, 2., 1./(Abs[i - j])^3], {i, 1, n}, {j, 1, n}]
. Also, it seems you're taking an inverse of the same matrix during each iteration, that seems unnecessary. $\endgroup$n=
, etc.) $\endgroup$M.Psi=m
using matrix inversion. This is very inefficient. For this purpose you should not useInverse[M]
, but ratherPsi=LinearSolve[M,m]
. $\endgroup$