0

Let's say I want to build a function of two variables from some expression I know only in some points. My syntax is for example like this:

A = {};
Monitor[For[e = -10, e <= 10, e += 0.1,
  For[w = -10, w <= 10, w += 0.1,
   A = Append[
     A, {w, e, 
      1/\[Pi] Im[(((1 + w)/(1 - w + w^2 + w^3) + 
            I w/(10 + 3 w^2 + 5 w^3)) (w + I/10000) + e + 
         Tanh[e])/((e + Tanh[e])^2 + (1/(
          1 + e^2 + 
           w^2)) - ((1 + w)/(1 - w + w^2 + w^3) + 
            I w/(10 + 3 w^2 + 5 w^3))^2 (w + I/10000)^2)]}]]], e]
A = Interpolation[A];

(you can copy it into Mathematica and run it)

It only creates an empty list and do a push_back when the element is computed. However, it drives me crazy that the higher the "e" is (I added the Monitor to see what the current value of e is), the slower the computation gets. Try to type e+=0.05 and w+=0.05 and you will see that the computation is so slow at the e = -6, you won't bother let it finish it. What is the reason? How to prevent this to happen? Is push_back in mathematica slow when array has some elements in it? But how can I do this differently? When I try nested Table[Table[ approach, I get redundant inner {} brackets that are not compatible with Interpolation[]. Thanks for the help!

user16320
  • 2,396
  • 15
  • 25

1 Answers1

2

Is this what your looking for? Using Table, it finishes in a few seconds. Flatten is used to keep the same structure as in your code.

A = Flatten[#,1]&@Table[{w, e, 
     1/\[Pi] Im[(((1 + w)/(1 - w + w^2 + w^3) + 
        I w/(10 + 3 w^2 + 5 w^3)) (w + I/10000) + e + Tanh[e])/((e + 
        Tanh[e])^2 + (1/(1 + e^2 + w^2)) - ((1 + w)/(1 - w + w^2 + w^3) + 
         I w/(10 + 3 w^2 + 5 w^3))^2 (w + I/10000)^2)]}, 
 {e, -10, 10, .1}, {w, -10, 10, .1}];

Append is known to be very slow, see for example:

You can interpolate with interp = Interpolation@A.

anderstood
  • 14,301
  • 2
  • 29
  • 80
  • No, the structure is wrong, if I interpolate that A, the result is rubbish. It has to be of the form {{w1, e1, A[w1,e1]}, {w2, e2, A[w2,e2]}, ...}

    What you produced is of the form: {w1, e1, A[w1,e1], w2, e2, A[w2,e2], ...} do you see the problem now?

    – user16320 Mar 06 '17 at 23:39
  • Have you seen the edit? – anderstood Mar 06 '17 at 23:40
  • Thank you, now it works! ^^ I'm bit frightened tho, because there are those mysterious mathematica symbols, @#&, but thanks anyway. – user16320 Mar 06 '17 at 23:45
  • This is the same as Flatten[Table[...],1] :) – anderstood Mar 06 '17 at 23:55
  • I think I'd need some "big 'flatten' tutorial", as I don't quite get how to regroup lists and lists within lists to my need. For example, I want to modify this so the variable 'e' does not run from -10 to 10, but just from 0 to 10 and make function even: Table[{{w, e, A[w,e]}, {w,-e, A[w,e]}},...] – user16320 Mar 07 '17 at 00:00
  • @user16320 Using Flatten (without the , 1] to flatten the list to {w, e, A, w, e, A ...}, then Partition[ ... , 3] could be a possibility. – anderstood Mar 07 '17 at 00:03
  • That works, thank you! Partition is a great thing. – user16320 Mar 07 '17 at 00:08