title: Optimizing numpy matrix operations (currently using a for loop)
body: <p>I've written some code to compute n matrices based on n items in a list, and then multiply all matrices together at the end.</p>
  
  <p>The code is relatively slow and I'd like to learn more about python optimization. I've used the profiling tools and identified the slow-down in my program is this matrix multiplication loop. </p>
  
  <p>I wonder if anyone has any recommendations for how I might speed this up, perhaps taking advantage of built in C-based functions in Python / NumPy?</p>
  
  <pre><code>def my_matrix(x):
  
      # Initialise overall matrix as an identity matrix
      # | M_11 M_12 |
      # | M_21 M_22 |
      M = np.matrix([[1, 0],[0, 1]])
  
      for z in z_all:
          param1 = func1(z)
          param2 = func2(x, z)
          param3 = func3(x, z)
  
          M_11 = param1 + param2
          M_12 = param1 - param2
          M_21 = param1 * param2
          M_22 = param1 / param2
  
          # Multiply matrix with overall master matrix
          M = M * np.matrix([[M_11, M_12],[M_21, M_22]])
      return M
  </code></pre>
  
  <p>From a little background reading, it seems that function calls are computationally expensive, and so, computing arrays for my params and then accessing the arrays could be more efficient than evaluating the function within the loop each time... e.g.</p>
  
  <pre><code> param1s = funcs(z_all)
   param2s = funcs(x, z_all)
   etc
  </code></pre>
  
  <p>and then in the for loop:</p>
  
  <pre><code>for i, z in enumerate(z_all):
      param1 = params1[i]
      param2 = params2[i]
   etc.
  </code></pre>
  
  <p>This is quicker, but only by about 10%, as the saving from fewer function calls is offset by time taken in array access using param1 = params1[i] in the loop.</p>
  
  <p>Does anyone have any recommendations please?</p>