[pypy-issue] [issue782] Order of calls changes performance

Ismael tracker at bugs.pypy.org
Wed Jul 6 07:00:36 CEST 2011


New submission from Ismael <ismaelgfk at gmail.com>:

In the following code, the order of calls alters the performance.

First case: running calc first, then calc_arr second:

ismael at chaos:~/Escritorio$ ~/pypy/bin/pypy slow.py 
Section time:  0.865699052811 -- Calc
Section time:  0.757493019104 -- Calc_arr

So, here, best time for calc_arr is 0.75s. It doesn't matter if I run it 10
times, it still about that fast.

Now, running calc_arr first and calc second:

ismael at chaos:~/Escritorio$ ~/pypy/bin/pypy slow.py 
Section time:  0.400774002075 -- Calc_arr
Section time:  1.53682088852 -- Calc

The method that took 0.7s now takes 0.4! And the one that took 0.8s now takes 1.5!


For comparison, PyPy latest (45351) is even worse:

ismael at chaos:~/Escritorio$
~/pypy/pypylatest/pypy-c-jit-45351-2630c86662b4-linux64/bin/pypy slow.py 
Section time:  0.940190792084 -- Calc
Section time:  0.925091981888 -- Calc_arr

ismael at chaos:~/Escritorio$
~/pypy/pypylatest/pypy-c-jit-45351-2630c86662b4-linux64/bin/pypy slow.py 
Section time:  0.418694019318 -- Calc_arr
Section time:  1.73908495903 -- Calc



Code modified from
http://technicaldiscovery.blogspot.com/2011/07/speeding-up-python-again.html

class Timer(object):
    def __enter__(self):
        self.start = time.time()
    def __exit__(self, exc_type, exc_val, tb):
        print "Section time: ", time.time() - self.start

import array
import time

dx = 0.1
dy = 0.1
dx2 = dx*dx
dy2 = dy*dy

def py_update(u,nx,ny):
    for i in xrange(1,nx-1):
        for j in xrange(1, ny-1):
            u[i][j] = ((u[i+1][j] + u[i-1][j]) * dy2 +
                      (u[i][j+1] + u[i][j-1]) * dx2) / (2*(dx2+dy2))

def calc(N, Niter=100):
    u = [[0.0]*N for i in xrange(N)]
    for i in xrange(N):
        u[0][i] = 1.0
    for i in range(Niter):
        py_update(u,N,N)
    return u
   
def calc_arr(N, Niter=100):
    u = [array.array("d", [0.0])*N for i in xrange(N)]
    for i in xrange(N):
        u[0][i] = 1.0
    for i in range(Niter):
        py_update(u,N,N)
    return u

#Compare this:
with Timer():
    u = calc_arr(150,1000)

with Timer():
    u = calc(150,1000)

#To this (comment the previous section):
with Timer():
    u = calc(150,1000)

with Timer():
    u = calc_arr(150,1000)

----------
messages: 2741
nosy: Ismael, pypy-issue
priority: bug
release: 1.5
status: unread
title: Order of calls changes performance

________________________________________
PyPy bug tracker <tracker at bugs.pypy.org>
<https://bugs.pypy.org/issue782>
________________________________________


More information about the pypy-issue mailing list