Updated to pybench 2.0.

See svn.python.org/external/pybench-2.0 for the original import of that
version.

Note that platform.py was not copied over from pybench-2.0 since
it is already part of Python 2.5.
This commit is contained in:
Marc-André Lemburg 2006-06-13 18:56:56 +00:00
parent ef7fe5f228
commit 7d9743dd6a
20 changed files with 1240 additions and 649 deletions

View file

@ -2,7 +2,7 @@ from pybench import Test
class SimpleIntegerArithmetic(Test): class SimpleIntegerArithmetic(Test):
version = 0.3 version = 2.0
operations = 5 * (3 + 5 + 5 + 3 + 3 + 3) operations = 5 * (3 + 5 + 5 + 3 + 3 + 3)
rounds = 120000 rounds = 120000
@ -157,9 +157,9 @@ class SimpleIntegerArithmetic(Test):
class SimpleFloatArithmetic(Test): class SimpleFloatArithmetic(Test):
version = 0.3 version = 2.0
operations = 5 * (3 + 5 + 5 + 3 + 3 + 3) operations = 5 * (3 + 5 + 5 + 3 + 3 + 3)
rounds = 100000 rounds = 120000
def test(self): def test(self):
@ -312,7 +312,7 @@ class SimpleFloatArithmetic(Test):
class SimpleIntFloatArithmetic(Test): class SimpleIntFloatArithmetic(Test):
version = 0.3 version = 2.0
operations = 5 * (3 + 5 + 5 + 3 + 3 + 3) operations = 5 * (3 + 5 + 5 + 3 + 3 + 3)
rounds = 120000 rounds = 120000
@ -468,9 +468,9 @@ class SimpleIntFloatArithmetic(Test):
class SimpleLongArithmetic(Test): class SimpleLongArithmetic(Test):
version = 0.3 version = 2.0
operations = 5 * (3 + 5 + 5 + 3 + 3 + 3) operations = 5 * (3 + 5 + 5 + 3 + 3 + 3)
rounds = 30000 rounds = 60000
def test(self): def test(self):
@ -623,9 +623,9 @@ class SimpleLongArithmetic(Test):
class SimpleComplexArithmetic(Test): class SimpleComplexArithmetic(Test):
version = 0.3 version = 2.0
operations = 5 * (3 + 5 + 5 + 3 + 3 + 3) operations = 5 * (3 + 5 + 5 + 3 + 3 + 3)
rounds = 40000 rounds = 80000
def test(self): def test(self):

View file

@ -2,7 +2,7 @@ from pybench import Test
class PythonFunctionCalls(Test): class PythonFunctionCalls(Test):
version = 0.3 version = 2.0
operations = 5*(1+4+4+2) operations = 5*(1+4+4+2)
rounds = 60000 rounds = 60000
@ -111,9 +111,9 @@ class PythonFunctionCalls(Test):
class BuiltinFunctionCalls(Test): class BuiltinFunctionCalls(Test):
version = 0.4 version = 2.0
operations = 5*(2+5+5+5) operations = 5*(2+5+5+5)
rounds = 30000 rounds = 60000
def test(self): def test(self):
@ -232,9 +232,9 @@ class BuiltinFunctionCalls(Test):
class PythonMethodCalls(Test): class PythonMethodCalls(Test):
version = 0.3 version = 2.0
operations = 5*(6 + 5 + 4) operations = 5*(6 + 5 + 4)
rounds = 20000 rounds = 30000
def test(self): def test(self):
@ -374,9 +374,9 @@ class PythonMethodCalls(Test):
class Recursion(Test): class Recursion(Test):
version = 0.3 version = 2.0
operations = 5 operations = 5
rounds = 50000 rounds = 100000
def test(self): def test(self):
@ -407,3 +407,98 @@ class Recursion(Test):
for i in xrange(self.rounds): for i in xrange(self.rounds):
pass pass
### Test to make Fredrik happy...
if __name__ == '__main__':
import timeit
if 0:
timeit.TestClass = PythonFunctionCalls
timeit.main(['-s', 'test = TestClass(); test.rounds = 1000',
'test.test()'])
else:
setup = """\
global f,f1,g,h
# define functions
def f():
pass
def f1(x):
pass
def g(a,b,c):
return a,b,c
def h(a,b,c,d=1,e=2,f=3):
return d,e,f
i = 1
"""
test = """\
f()
f1(i)
f1(i)
f1(i)
f1(i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
h(i,i,3,i,i)
h(i,i,i,2,i,3)
f()
f1(i)
f1(i)
f1(i)
f1(i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
h(i,i,3,i,i)
h(i,i,i,2,i,3)
f()
f1(i)
f1(i)
f1(i)
f1(i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
h(i,i,3,i,i)
h(i,i,i,2,i,3)
f()
f1(i)
f1(i)
f1(i)
f1(i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
h(i,i,3,i,i)
h(i,i,i,2,i,3)
f()
f1(i)
f1(i)
f1(i)
f1(i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
g(i,i,i)
h(i,i,3,i,i)
h(i,i,i,2,i,3)
"""
timeit.main(['-s', setup,
test])

View file

@ -358,7 +358,7 @@ class Application:
except self.InternalError: except self.InternalError:
print print
print '* Internal Error' print '* Internal Error (use --debug to display the traceback)'
if self.debug: if self.debug:
print print
traceback.print_exc(20, sys.stdout) traceback.print_exc(20, sys.stdout)

View file

@ -2,7 +2,7 @@ from pybench import Test
class IfThenElse(Test): class IfThenElse(Test):
version = 0.31 version = 2.0
operations = 30*3 # hard to say... operations = 30*3 # hard to say...
rounds = 150000 rounds = 150000
@ -469,9 +469,9 @@ class IfThenElse(Test):
class NestedForLoops(Test): class NestedForLoops(Test):
version = 0.3 version = 2.0
operations = 1000*10*5 operations = 1000*10*5
rounds = 150 rounds = 300
def test(self): def test(self):
@ -494,9 +494,9 @@ class NestedForLoops(Test):
class ForLoops(Test): class ForLoops(Test):
version = 0.1 version = 2.0
operations = 5 * 5 operations = 5 * 5
rounds = 8000 rounds = 10000
def test(self): def test(self):

View file

@ -2,9 +2,9 @@ from pybench import Test
class DictCreation(Test): class DictCreation(Test):
version = 0.3 version = 2.0
operations = 5*(5 + 5) operations = 5*(5 + 5)
rounds = 60000 rounds = 80000
def test(self): def test(self):
@ -77,7 +77,7 @@ class DictCreation(Test):
class DictWithStringKeys(Test): class DictWithStringKeys(Test):
version = 0.1 version = 2.0
operations = 5*(6 + 6) operations = 5*(6 + 6)
rounds = 200000 rounds = 200000
@ -166,9 +166,9 @@ class DictWithStringKeys(Test):
class DictWithFloatKeys(Test): class DictWithFloatKeys(Test):
version = 0.1 version = 2.0
operations = 5*(6 + 6) operations = 5*(6 + 6)
rounds = 200000 rounds = 150000
def test(self): def test(self):
@ -255,7 +255,7 @@ class DictWithFloatKeys(Test):
class DictWithIntegerKeys(Test): class DictWithIntegerKeys(Test):
version = 0.1 version = 2.0
operations = 5*(6 + 6) operations = 5*(6 + 6)
rounds = 200000 rounds = 200000
@ -344,13 +344,14 @@ class DictWithIntegerKeys(Test):
class SimpleDictManipulation(Test): class SimpleDictManipulation(Test):
version = 0.3 version = 2.0
operations = 5*(6 + 6 + 6 + 6) operations = 5*(6 + 6 + 6 + 6)
rounds = 50000 rounds = 100000
def test(self): def test(self):
d = {} d = {}
has_key = d.has_key
for i in xrange(self.rounds): for i in xrange(self.rounds):
@ -368,12 +369,12 @@ class SimpleDictManipulation(Test):
x = d[4] x = d[4]
x = d[5] x = d[5]
d.has_key(0) has_key(0)
d.has_key(2) has_key(2)
d.has_key(4) has_key(4)
d.has_key(6) has_key(6)
d.has_key(8) has_key(8)
d.has_key(10) has_key(10)
del d[0] del d[0]
del d[1] del d[1]
@ -396,12 +397,12 @@ class SimpleDictManipulation(Test):
x = d[4] x = d[4]
x = d[5] x = d[5]
d.has_key(0) has_key(0)
d.has_key(2) has_key(2)
d.has_key(4) has_key(4)
d.has_key(6) has_key(6)
d.has_key(8) has_key(8)
d.has_key(10) has_key(10)
del d[0] del d[0]
del d[1] del d[1]
@ -424,12 +425,12 @@ class SimpleDictManipulation(Test):
x = d[4] x = d[4]
x = d[5] x = d[5]
d.has_key(0) has_key(0)
d.has_key(2) has_key(2)
d.has_key(4) has_key(4)
d.has_key(6) has_key(6)
d.has_key(8) has_key(8)
d.has_key(10) has_key(10)
del d[0] del d[0]
del d[1] del d[1]
@ -452,12 +453,12 @@ class SimpleDictManipulation(Test):
x = d[4] x = d[4]
x = d[5] x = d[5]
d.has_key(0) has_key(0)
d.has_key(2) has_key(2)
d.has_key(4) has_key(4)
d.has_key(6) has_key(6)
d.has_key(8) has_key(8)
d.has_key(10) has_key(10)
del d[0] del d[0]
del d[1] del d[1]
@ -480,12 +481,12 @@ class SimpleDictManipulation(Test):
x = d[4] x = d[4]
x = d[5] x = d[5]
d.has_key(0) has_key(0)
d.has_key(2) has_key(2)
d.has_key(4) has_key(4)
d.has_key(6) has_key(6)
d.has_key(8) has_key(8)
d.has_key(10) has_key(10)
del d[0] del d[0]
del d[1] del d[1]
@ -497,6 +498,7 @@ class SimpleDictManipulation(Test):
def calibrate(self): def calibrate(self):
d = {} d = {}
has_key = d.has_key
for i in xrange(self.rounds): for i in xrange(self.rounds):
pass pass

View file

@ -2,9 +2,9 @@ from pybench import Test
class TryRaiseExcept(Test): class TryRaiseExcept(Test):
version = 0.1 version = 2.0
operations = 2 + 3 operations = 2 + 3 + 3
rounds = 60000 rounds = 80000
def test(self): def test(self):
@ -31,6 +31,18 @@ class TryRaiseExcept(Test):
raise error,"something" raise error,"something"
except: except:
pass pass
try:
raise error("something")
except:
pass
try:
raise error("something")
except:
pass
try:
raise error("something")
except:
pass
def calibrate(self): def calibrate(self):
@ -42,9 +54,9 @@ class TryRaiseExcept(Test):
class TryExcept(Test): class TryExcept(Test):
version = 0.1 version = 2.0
operations = 15 * 10 operations = 15 * 10
rounds = 200000 rounds = 150000
def test(self): def test(self):
@ -677,3 +689,11 @@ class TryExcept(Test):
for i in xrange(self.rounds): for i in xrange(self.rounds):
pass pass
### Test to make Fredrik happy...
if __name__ == '__main__':
import timeit
timeit.TestClass = TryRaiseExcept
timeit.main(['-s', 'test = TestClass(); test.rounds = 1000',
'test.test()'])

View file

@ -6,9 +6,9 @@ import package.submodule
class SecondImport(Test): class SecondImport(Test):
version = 0.1 version = 2.0
operations = 5 * 5 operations = 5 * 5
rounds = 20000 rounds = 40000
def test(self): def test(self):
@ -51,9 +51,9 @@ class SecondImport(Test):
class SecondPackageImport(Test): class SecondPackageImport(Test):
version = 0.1 version = 2.0
operations = 5 * 5 operations = 5 * 5
rounds = 20000 rounds = 40000
def test(self): def test(self):
@ -95,9 +95,9 @@ class SecondPackageImport(Test):
class SecondSubmoduleImport(Test): class SecondSubmoduleImport(Test):
version = 0.1 version = 2.0
operations = 5 * 5 operations = 5 * 5
rounds = 20000 rounds = 40000
def test(self): def test(self):

View file

@ -2,9 +2,9 @@ from pybench import Test
class CreateInstances(Test): class CreateInstances(Test):
version = 0.2 version = 2.0
operations = 3 + 7 + 4 operations = 3 + 7 + 4
rounds = 60000 rounds = 80000
def test(self): def test(self):

View file

@ -2,22 +2,23 @@ from pybench import Test
class SimpleListManipulation(Test): class SimpleListManipulation(Test):
version = 0.3 version = 2.0
operations = 5* (6 + 6 + 6) operations = 5* (6 + 6 + 6)
rounds = 60000 rounds = 130000
def test(self): def test(self):
l = [] l = []
append = l.append
for i in xrange(self.rounds): for i in xrange(self.rounds):
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -33,12 +34,12 @@ class SimpleListManipulation(Test):
x = l[4] x = l[4]
x = l[5] x = l[5]
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -54,12 +55,12 @@ class SimpleListManipulation(Test):
x = l[4] x = l[4]
x = l[5] x = l[5]
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -75,12 +76,12 @@ class SimpleListManipulation(Test):
x = l[4] x = l[4]
x = l[5] x = l[5]
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -96,12 +97,12 @@ class SimpleListManipulation(Test):
x = l[4] x = l[4]
x = l[5] x = l[5]
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l.append(2) append(2)
l.append(3) append(3)
l.append(4) append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -124,15 +125,16 @@ class SimpleListManipulation(Test):
def calibrate(self): def calibrate(self):
l = [] l = []
append = l.append
for i in xrange(self.rounds): for i in xrange(self.rounds):
pass pass
class ListSlicing(Test): class ListSlicing(Test):
version = 0.4 version = 2.0
operations = 25*(3+1+2+1) operations = 25*(3+1+2+1)
rounds = 400 rounds = 800
def test(self): def test(self):
@ -141,7 +143,7 @@ class ListSlicing(Test):
for i in xrange(self.rounds): for i in xrange(self.rounds):
l = range(100) l = n[:]
for j in r: for j in r:
@ -159,17 +161,14 @@ class ListSlicing(Test):
r = range(25) r = range(25)
for i in xrange(self.rounds): for i in xrange(self.rounds):
l = range(100)
for j in r: for j in r:
pass pass
class SmallLists(Test): class SmallLists(Test):
version = 0.3 version = 2.0
operations = 5*(1+ 6 + 6 + 3 + 1) operations = 5*(1+ 6 + 6 + 3 + 1)
rounds = 60000 rounds = 80000
def test(self): def test(self):
@ -177,12 +176,13 @@ class SmallLists(Test):
l = [] l = []
l.append(2) append = l.append
l.append(3) append(2)
l.append(4) append(3)
l.append(2) append(4)
l.append(3) append(2)
l.append(4) append(3)
append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -199,12 +199,13 @@ class SmallLists(Test):
l = [] l = []
l.append(2) append = l.append
l.append(3) append(2)
l.append(4) append(3)
l.append(2) append(4)
l.append(3) append(2)
l.append(4) append(3)
append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -221,12 +222,13 @@ class SmallLists(Test):
l = [] l = []
l.append(2) append = l.append
l.append(3) append(2)
l.append(4) append(3)
l.append(2) append(4)
l.append(3) append(2)
l.append(4) append(3)
append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -243,12 +245,13 @@ class SmallLists(Test):
l = [] l = []
l.append(2) append = l.append
l.append(3) append(2)
l.append(4) append(3)
l.append(2) append(4)
l.append(3) append(2)
l.append(4) append(3)
append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -265,12 +268,13 @@ class SmallLists(Test):
l = [] l = []
l.append(2) append = l.append
l.append(3) append(2)
l.append(4) append(3)
l.append(2) append(4)
l.append(3) append(2)
l.append(4) append(3)
append(4)
l[0] = 3 l[0] = 3
l[1] = 4 l[1] = 4
@ -288,4 +292,4 @@ class SmallLists(Test):
def calibrate(self): def calibrate(self):
for i in xrange(self.rounds): for i in xrange(self.rounds):
l = [] pass

View file

@ -2,7 +2,7 @@ from pybench import Test
class SpecialClassAttribute(Test): class SpecialClassAttribute(Test):
version = 0.3 version = 2.0
operations = 5*(12 + 12) operations = 5*(12 + 12)
rounds = 100000 rounds = 100000
@ -183,7 +183,7 @@ class SpecialClassAttribute(Test):
class NormalClassAttribute(Test): class NormalClassAttribute(Test):
version = 0.3 version = 2.0
operations = 5*(12 + 12) operations = 5*(12 + 12)
rounds = 100000 rounds = 100000
@ -369,7 +369,7 @@ class NormalClassAttribute(Test):
class SpecialInstanceAttribute(Test): class SpecialInstanceAttribute(Test):
version = 0.3 version = 2.0
operations = 5*(12 + 12) operations = 5*(12 + 12)
rounds = 100000 rounds = 100000
@ -557,7 +557,7 @@ class SpecialInstanceAttribute(Test):
class NormalInstanceAttribute(Test): class NormalInstanceAttribute(Test):
version = 0.3 version = 2.0
operations = 5*(12 + 12) operations = 5*(12 + 12)
rounds = 100000 rounds = 100000
@ -745,7 +745,7 @@ class NormalInstanceAttribute(Test):
class BuiltinMethodLookup(Test): class BuiltinMethodLookup(Test):
version = 0.3 version = 2.0
operations = 5*(3*5 + 3*5) operations = 5*(3*5 + 3*5)
rounds = 70000 rounds = 70000

11
Tools/pybench/NewInstances.py Executable file → Normal file
View file

@ -1,8 +1,17 @@
from pybench import Test from pybench import Test
# Check for new-style class support:
try:
class c(object):
pass
except NameError:
raise ImportError
###
class CreateNewInstances(Test): class CreateNewInstances(Test):
version = 0.1 version = 2.0
operations = 3 + 7 + 4 operations = 3 + 7 + 4
rounds = 60000 rounds = 60000

View file

@ -2,7 +2,7 @@ from pybench import Test
class CompareIntegers(Test): class CompareIntegers(Test):
version = 0.1 version = 2.0
operations = 30 * 5 operations = 30 * 5
rounds = 120000 rounds = 120000
@ -198,9 +198,9 @@ class CompareIntegers(Test):
class CompareFloats(Test): class CompareFloats(Test):
version = 0.1 version = 2.0
operations = 30 * 5 operations = 30 * 5
rounds = 60000 rounds = 80000
def test(self): def test(self):
@ -394,7 +394,7 @@ class CompareFloats(Test):
class CompareFloatsIntegers(Test): class CompareFloatsIntegers(Test):
version = 0.1 version = 2.0
operations = 30 * 5 operations = 30 * 5
rounds = 60000 rounds = 60000
@ -590,9 +590,9 @@ class CompareFloatsIntegers(Test):
class CompareLongs(Test): class CompareLongs(Test):
version = 0.1 version = 2.0
operations = 30 * 5 operations = 30 * 5
rounds = 60000 rounds = 70000
def test(self): def test(self):

View file

@ -28,12 +28,37 @@ and then print out a report to stdout.
Micro-Manual Micro-Manual
------------ ------------
Run 'pybench.py -h' to see the help screen. Run 'pybench.py -h' to see the help screen. Run 'pybench.py' to run
Run 'pybench.py' to just let the benchmark suite do it's thing and the benchmark suite using default settings and 'pybench.py -f <file>'
'pybench.py -f <file>' to have it store the results in a file too. to have it store the results in a file too.
It is usually a good idea to run pybench.py multiple times to see
whether the environment, timers and benchmark run-times are suitable
for doing benchmark tests.
You can use the comparison feature of pybench.py ('pybench.py -c
<file>') to check how well the system behaves in comparison to a
reference run.
If the differences are well below 10% for each test, then you have a
system that is good for doing benchmark testings. Of you get random
differences of more than 10% or significant differences between the
values for minimum and average time, then you likely have some
background processes running which cause the readings to become
inconsistent. Examples include: web-browsers, email clients, RSS
readers, music players, backup programs, etc.
If you are only interested in a few tests of the whole suite, you can
use the filtering option, e.g. 'pybench.py -t string' will only
run/show the tests that have 'string' in their name.
This is the current output of pybench.py --help: This is the current output of pybench.py --help:
"""
------------------------------------------------------------------------
PYBENCH - a benchmark test suite for Python interpreters/compilers.
------------------------------------------------------------------------
Synopsis: Synopsis:
pybench.py [option] files... pybench.py [option] files...
@ -42,14 +67,14 @@ Options and default settings:
-f arg save benchmark to file arg () -f arg save benchmark to file arg ()
-c arg compare benchmark with the one in file arg () -c arg compare benchmark with the one in file arg ()
-s arg show benchmark in file arg, then exit () -s arg show benchmark in file arg, then exit ()
-S show statistics of benchmarks (0) -w arg set warp factor to arg (10)
-w arg set warp factor to arg (20) -t arg run only tests with names matching arg ()
-d hide noise in compares (0) -C arg set the number of calibration runs to arg (20)
--no-gc disable garbage collection (0) -d hide noise in comparisons (0)
--no-syscheck "disable" sys check interval (set to sys.maxint) (0) -v verbose output (not recommended) (0)
-t arg tests containing substring () --with-gc enable garbage collection (0)
-C arg number of calibration runs (20) --with-syscheck use default sys check interval (0)
-v generate verbose output --timer arg use given timer (time.time)
-h show this help text -h show this help text
--help show this help text --help show this help text
--debug enable debugging --debug enable debugging
@ -57,17 +82,23 @@ Options and default settings:
--examples show examples of usage --examples show examples of usage
Version: Version:
1.3 2.0
The normal operation is to run the suite and display the The normal operation is to run the suite and display the
results. Use -f to save them for later reuse or comparisms. results. Use -f to save them for later reuse or comparisons.
Available timers:
time.time
time.clock
systimes.processtime
Examples: Examples:
python1.5 pybench.py -w 100 -f p15 python2.1 pybench.py -f p21.pybench
python1.4 pybench.py -w 100 -f p14 python2.5 pybench.py -f p25.pybench
python pybench.py -s p15 -c p14 python pybench.py -s p25.pybench -c p21.pybench
"""
License License
------- -------
@ -78,184 +109,103 @@ See LICENSE file.
Sample output Sample output
------------- -------------
PYBENCH 1.3 """
-------------------------------------------------------------------------------
PYBENCH 2.0
-------------------------------------------------------------------------------
* using Python 2.4.2
* disabled garbage collection
* system check interval set to maximum: 2147483647
* using timer: time.time
Calibrating tests. Please wait...
Running 10 round(s) of the suite at warp factor 10:
* Round 1 done in 6.388 seconds.
* Round 2 done in 6.485 seconds.
* Round 3 done in 6.786 seconds.
...
* Round 10 done in 6.546 seconds.
-------------------------------------------------------------------------------
Benchmark: 2006-06-12 12:09:25
-------------------------------------------------------------------------------
Rounds: 10
Warp: 10
Timer: time.time
Machine Details: Machine Details:
Platform ID: Linux-2.6.8-24.19-default-x86_64-with-SuSE-9.2-x86-64 Platform ID: Linux-2.6.8-24.19-default-x86_64-with-SuSE-9.2-x86-64
Executable: /home/lemburg/projects/Python/Installation/bin/python Processor: x86_64
Python: 2.5a1.0
Python:
Executable: /usr/local/bin/python
Version: 2.4.2
Compiler: GCC 3.3.4 (pre 3.3.5 20040809) Compiler: GCC 3.3.4 (pre 3.3.5 20040809)
Build: Apr 9 2006 01:50:57 (#trunk) Bits: 64bit
Build: Oct 1 2005 15:24:35 (#1)
Searching for tests... Unicode: UCS2
BuiltinFunctionCalls
BuiltinMethodLookup
CompareFloats
CompareFloatsIntegers
CompareIntegers
CompareInternedStrings
CompareLongs
CompareStrings
CompareUnicode
ConcatStrings
ConcatUnicode
CreateInstances
CreateStringsWithConcat
CreateUnicodeWithConcat
DictCreation
DictWithFloatKeys
DictWithIntegerKeys
DictWithStringKeys
ForLoops
IfThenElse
ListSlicing
NestedForLoops
NormalClassAttribute
NormalInstanceAttribute
PythonFunctionCalls
PythonMethodCalls
Recursion
SecondImport
SecondPackageImport
SecondSubmoduleImport
SimpleComplexArithmetic
SimpleDictManipulation
SimpleFloatArithmetic
SimpleIntFloatArithmetic
SimpleIntegerArithmetic
SimpleListManipulation
SimpleLongArithmetic
SmallLists
SmallTuples
SpecialClassAttribute
SpecialInstanceAttribute
StringMappings
StringPredicates
StringSlicing
TryExcept
TryRaiseExcept
TupleSlicing
UnicodeMappings
UnicodePredicates
UnicodeProperties
UnicodeSlicing
Running 10 round(s) of the suite:
...
Round 10 real abs overhead
BuiltinFunctionCalls: 0.030r 0.030a 0.000o
BuiltinMethodLookup: 0.059r 0.060a 0.001o
CompareFloats: 0.050r 0.050a 0.000o
CompareFloatsIntegers: 0.050r 0.050a 0.000o
CompareIntegers: 0.070r 0.070a 0.000o
CompareInternedStrings: 0.039r 0.040a 0.001o
CompareLongs: 0.050r 0.050a 0.000o
CompareStrings: 0.060r 0.060a 0.000o
CompareUnicode: 0.060r 0.060a 0.000o
ConcatStrings: 0.040r 0.040a 0.000o
ConcatUnicode: 0.050r 0.050a 0.000o
CreateInstances: 0.050r 0.050a 0.000o
CreateStringsWithConcat: 0.029r 0.030a 0.001o
CreateUnicodeWithConcat: 0.060r 0.060a 0.000o
DictCreation: 0.040r 0.040a 0.000o
DictWithFloatKeys: 0.089r 0.090a 0.000o
DictWithIntegerKeys: 0.059r 0.060a 0.001o
DictWithStringKeys: 0.070r 0.070a 0.001o
ForLoops: 0.050r 0.050a 0.000o
IfThenElse: 0.070r 0.070a 0.000o
ListSlicing: 0.030r 0.030a 0.000o
NestedForLoops: 0.030r 0.030a 0.000o
NormalClassAttribute: 0.060r 0.060a 0.000o
NormalInstanceAttribute: 0.060r 0.060a 0.000o
PythonFunctionCalls: 0.060r 0.060a 0.000o
PythonMethodCalls: 0.050r 0.050a 0.000o
Recursion: 0.050r 0.050a 0.000o
SecondImport: 0.030r 0.030a 0.000o
SecondPackageImport: 0.030r 0.030a 0.000o
SecondSubmoduleImport: 0.040r 0.040a 0.000o
SimpleComplexArithmetic: 0.030r 0.030a 0.000o
SimpleDictManipulation: 0.040r 0.040a 0.000o
SimpleFloatArithmetic: 0.050r 0.050a 0.001o
SimpleIntFloatArithmetic: 0.060r 0.060a 0.000o
SimpleIntegerArithmetic: 0.060r 0.060a 0.000o
SimpleListManipulation: 0.030r 0.030a 0.000o
SimpleLongArithmetic: 0.030r 0.030a 0.000o
SmallLists: 0.050r 0.050a 0.000o
SmallTuples: 0.050r 0.050a 0.000o
SpecialClassAttribute: 0.060r 0.060a 0.000o
SpecialInstanceAttribute: 0.079r 0.080a 0.001o
StringMappings: 0.060r 0.060a 0.000o
StringPredicates: 0.049r 0.050a 0.001o
StringSlicing: 0.039r 0.040a 0.000o
TryExcept: 0.079r 0.080a 0.001o
TryRaiseExcept: 0.059r 0.060a 0.001o
TupleSlicing: 0.050r 0.050a 0.000o
UnicodeMappings: 0.070r 0.070a 0.001o
UnicodePredicates: 0.059r 0.060a 0.001o
UnicodeProperties: 0.059r 0.060a 0.001o
UnicodeSlicing: 0.050r 0.050a 0.000o
----------------------
Average round time: 2.937 seconds
Tests: per run per oper. overhead Test minimum average operation overhead
------------------------------------------------------------------------ -------------------------------------------------------------------------------
BuiltinFunctionCalls: 29.85 ms 0.23 us 0.00 ms BuiltinFunctionCalls: 126ms 145ms 0.28us 0.274ms
BuiltinMethodLookup: 66.85 ms 0.13 us 0.50 ms BuiltinMethodLookup: 124ms 130ms 0.12us 0.316ms
CompareFloats: 43.00 ms 0.10 us 0.00 ms CompareFloats: 109ms 110ms 0.09us 0.361ms
CompareFloatsIntegers: 51.80 ms 0.12 us 0.00 ms CompareFloatsIntegers: 100ms 104ms 0.12us 0.271ms
CompareIntegers: 70.70 ms 0.08 us 0.50 ms CompareIntegers: 137ms 138ms 0.08us 0.542ms
CompareInternedStrings: 41.40 ms 0.08 us 0.50 ms CompareInternedStrings: 124ms 127ms 0.08us 1.367ms
CompareLongs: 47.90 ms 0.11 us 0.00 ms CompareLongs: 100ms 104ms 0.10us 0.316ms
CompareStrings: 58.50 ms 0.12 us 0.50 ms CompareStrings: 111ms 115ms 0.12us 0.929ms
CompareUnicode: 56.55 ms 0.15 us 0.50 ms CompareUnicode: 108ms 128ms 0.17us 0.693ms
ConcatStrings: 44.75 ms 0.30 us 0.00 ms ConcatStrings: 142ms 155ms 0.31us 0.562ms
ConcatUnicode: 54.55 ms 0.36 us 0.50 ms ConcatUnicode: 119ms 127ms 0.42us 0.384ms
CreateInstances: 50.95 ms 1.21 us 0.00 ms CreateInstances: 123ms 128ms 1.14us 0.367ms
CreateStringsWithConcat: 28.85 ms 0.14 us 0.50 ms CreateNewInstances: 121ms 126ms 1.49us 0.335ms
CreateUnicodeWithConcat: 53.75 ms 0.27 us 0.00 ms CreateStringsWithConcat: 130ms 135ms 0.14us 0.916ms
DictCreation: 41.90 ms 0.28 us 0.00 ms CreateUnicodeWithConcat: 130ms 135ms 0.34us 0.361ms
DictWithFloatKeys: 88.50 ms 0.15 us 0.50 ms DictCreation: 108ms 109ms 0.27us 0.361ms
DictWithIntegerKeys: 62.55 ms 0.10 us 0.50 ms DictWithFloatKeys: 149ms 153ms 0.17us 0.678ms
DictWithStringKeys: 60.50 ms 0.10 us 0.50 ms DictWithIntegerKeys: 124ms 126ms 0.11us 0.915ms
ForLoops: 46.90 ms 4.69 us 0.00 ms DictWithStringKeys: 114ms 117ms 0.10us 0.905ms
IfThenElse: 60.55 ms 0.09 us 0.00 ms ForLoops: 110ms 111ms 4.46us 0.063ms
ListSlicing: 29.90 ms 8.54 us 0.00 ms IfThenElse: 118ms 119ms 0.09us 0.685ms
NestedForLoops: 33.95 ms 0.10 us 0.00 ms ListSlicing: 116ms 120ms 8.59us 0.103ms
NormalClassAttribute: 62.75 ms 0.10 us 0.50 ms NestedForLoops: 125ms 137ms 0.09us 0.019ms
NormalInstanceAttribute: 61.80 ms 0.10 us 0.50 ms NormalClassAttribute: 124ms 136ms 0.11us 0.457ms
PythonFunctionCalls: 60.00 ms 0.36 us 0.00 ms NormalInstanceAttribute: 110ms 117ms 0.10us 0.454ms
PythonMethodCalls: 50.00 ms 0.67 us 0.00 ms PythonFunctionCalls: 107ms 113ms 0.34us 0.271ms
Recursion: 46.85 ms 3.75 us 0.00 ms PythonMethodCalls: 140ms 149ms 0.66us 0.141ms
SecondImport: 35.00 ms 1.40 us 0.00 ms Recursion: 156ms 166ms 3.32us 0.452ms
SecondPackageImport: 32.00 ms 1.28 us 0.00 ms SecondImport: 112ms 118ms 1.18us 0.180ms
SecondSubmoduleImport: 38.00 ms 1.52 us 0.00 ms SecondPackageImport: 118ms 127ms 1.27us 0.180ms
SimpleComplexArithmetic: 26.85 ms 0.12 us 0.00 ms SecondSubmoduleImport: 140ms 151ms 1.51us 0.180ms
SimpleDictManipulation: 40.85 ms 0.14 us 0.00 ms SimpleComplexArithmetic: 128ms 139ms 0.16us 0.361ms
SimpleFloatArithmetic: 48.70 ms 0.09 us 0.50 ms SimpleDictManipulation: 134ms 136ms 0.11us 0.452ms
SimpleIntFloatArithmetic: 57.70 ms 0.09 us 0.00 ms SimpleFloatArithmetic: 110ms 113ms 0.09us 0.571ms
SimpleIntegerArithmetic: 58.75 ms 0.09 us 0.50 ms SimpleIntFloatArithmetic: 106ms 111ms 0.08us 0.548ms
SimpleListManipulation: 34.80 ms 0.13 us 0.00 ms SimpleIntegerArithmetic: 106ms 109ms 0.08us 0.544ms
SimpleLongArithmetic: 30.95 ms 0.19 us 0.50 ms SimpleListManipulation: 103ms 113ms 0.10us 0.587ms
SmallLists: 47.60 ms 0.19 us 0.00 ms SimpleLongArithmetic: 112ms 118ms 0.18us 0.271ms
SmallTuples: 48.80 ms 0.20 us 0.50 ms SmallLists: 105ms 116ms 0.17us 0.366ms
SpecialClassAttribute: 61.70 ms 0.10 us 0.00 ms SmallTuples: 108ms 128ms 0.24us 0.406ms
SpecialInstanceAttribute: 76.70 ms 0.13 us 0.50 ms SpecialClassAttribute: 119ms 136ms 0.11us 0.453ms
StringMappings: 58.70 ms 0.47 us 0.00 ms SpecialInstanceAttribute: 143ms 155ms 0.13us 0.454ms
StringPredicates: 50.00 ms 0.18 us 1.00 ms StringMappings: 115ms 121ms 0.48us 0.405ms
StringSlicing: 39.65 ms 0.23 us 0.50 ms StringPredicates: 120ms 129ms 0.18us 2.064ms
TryExcept: 84.45 ms 0.06 us 0.50 ms StringSlicing: 111ms 127ms 0.23us 0.781ms
TryRaiseExcept: 61.75 ms 4.12 us 0.50 ms TryExcept: 125ms 126ms 0.06us 0.681ms
TupleSlicing: 48.95 ms 0.47 us 0.00 ms TryRaiseExcept: 133ms 137ms 2.14us 0.361ms
UnicodeMappings: 71.50 ms 3.97 us 0.50 ms TupleSlicing: 117ms 120ms 0.46us 0.066ms
UnicodePredicates: 52.75 ms 0.23 us 1.00 ms UnicodeMappings: 156ms 160ms 4.44us 0.429ms
UnicodeProperties: 61.90 ms 0.31 us 1.00 ms UnicodePredicates: 117ms 121ms 0.22us 2.487ms
UnicodeSlicing: 53.75 ms 0.31 us 0.50 ms UnicodeProperties: 115ms 153ms 0.38us 2.070ms
------------------------------------------------------------------------ UnicodeSlicing: 126ms 129ms 0.26us 0.689ms
Average round time: 2937.00 ms -------------------------------------------------------------------------------
Totals: 6283ms 6673ms
"""
________________________________________________________________________ ________________________________________________________________________
Writing New Tests Writing New Tests
@ -293,7 +243,7 @@ class IntegerCounting(Test):
# Number of rounds to execute per test run. This should be # Number of rounds to execute per test run. This should be
# adjusted to a figure that results in a test run-time of between # adjusted to a figure that results in a test run-time of between
# 20-50 seconds. # 1-2 seconds (at warp 1).
rounds = 100000 rounds = 100000
def test(self): def test(self):
@ -377,6 +327,41 @@ longer strictly comparable with previous runs, the '.version' class
variable should be updated. Therefafter, comparisons with previous variable should be updated. Therefafter, comparisons with previous
versions of the test will list as "n/a" to reflect the change. versions of the test will list as "n/a" to reflect the change.
Version History
---------------
2.0: rewrote parts of pybench which resulted in more repeatable
timings:
- made timer a parameter
- changed the platform default timer to use high-resolution
timers rather than process timers (which have a much lower
resolution)
- added option to select timer
- added process time timer (using systimes.py)
- changed to use min() as timing estimator (average
is still taken as well to provide an idea of the difference)
- garbage collection is turned off per default
- sys check interval is set to the highest possible value
- calibration is now a separate step and done using
a different strategy that allows measuring the test
overhead more accurately
- modified the tests to each give a run-time of between
100-200ms using warp 10
- changed default warp factor to 10 (from 20)
- compared results with timeit.py and confirmed measurements
- bumped all test versions to 2.0
- updated platform.py to the latest version
- changed the output format a bit to make it look
nicer
- refactored the APIs somewhat
1.3+: Steve Holden added the NewInstances test and the filtering
option during the NeedForSpeed sprint; this also triggered a long
discussion on how to improve benchmark timing and finally
resulted in the release of 2.0
1.3: initial checkin into the Python SVN repository
Have fun, Have fun,
-- --
Marc-Andre Lemburg Marc-Andre Lemburg

View file

@ -14,7 +14,7 @@
# Defaults # Defaults
Number_of_rounds = 10 Number_of_rounds = 10
Warp_factor = 20 Warp_factor = 10
# Import tests # Import tests
from Arithmetic import * from Arithmetic import *
@ -24,8 +24,8 @@ from Lookups import *
from Instances import * from Instances import *
try: try:
from NewInstances import * from NewInstances import *
except: except ImportError:
print "Cannot test new-style objects" pass
from Lists import * from Lists import *
from Tuples import * from Tuples import *
from Dict import * from Dict import *

View file

@ -3,9 +3,9 @@ from string import join
class ConcatStrings(Test): class ConcatStrings(Test):
version = 0.1 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 60000 rounds = 100000
def test(self): def test(self):
@ -85,7 +85,7 @@ class ConcatStrings(Test):
class CompareStrings(Test): class CompareStrings(Test):
version = 0.2 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 200000 rounds = 200000
@ -167,9 +167,9 @@ class CompareStrings(Test):
class CompareInternedStrings(Test): class CompareInternedStrings(Test):
version = 0.1 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 200000 rounds = 300000
def test(self): def test(self):
@ -249,9 +249,9 @@ class CompareInternedStrings(Test):
class CreateStringsWithConcat(Test): class CreateStringsWithConcat(Test):
version = 0.1 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 80000 rounds = 200000
def test(self): def test(self):
@ -324,9 +324,9 @@ class CreateStringsWithConcat(Test):
class StringSlicing(Test): class StringSlicing(Test):
version = 0.1 version = 2.0
operations = 5 * 7 operations = 5 * 7
rounds = 100000 rounds = 160000
def test(self): def test(self):
@ -387,7 +387,7 @@ if hasattr('', 'lower'):
class StringMappings(Test): class StringMappings(Test):
version = 0.1 version = 2.0
operations = 3 * (5 + 4 + 2 + 1) operations = 3 * (5 + 4 + 2 + 1)
rounds = 70000 rounds = 70000
@ -460,9 +460,9 @@ if hasattr('', 'lower'):
class StringPredicates(Test): class StringPredicates(Test):
version = 0.1 version = 2.0
operations = 10 * 7 operations = 10 * 7
rounds = 80000 rounds = 100000
def test(self): def test(self):

View file

@ -2,18 +2,17 @@ from pybench import Test
class TupleSlicing(Test): class TupleSlicing(Test):
version = 0.31 version = 2.0
operations = 3 * 25 * 10 * 7 operations = 3 * 25 * 10 * 7
rounds = 400 rounds = 500
def test(self): def test(self):
r = range(25) r = range(25)
t = tuple(range(100))
for i in xrange(self.rounds): for i in xrange(self.rounds):
t = tuple(range(100))
for j in r: for j in r:
m = t[50:] m = t[50:]
@ -259,20 +258,17 @@ class TupleSlicing(Test):
def calibrate(self): def calibrate(self):
r = range(25) r = range(25)
for i in xrange(self.rounds):
t = tuple(range(100)) t = tuple(range(100))
for i in xrange(self.rounds):
for j in r: for j in r:
pass pass
class SmallTuples(Test): class SmallTuples(Test):
version = 0.3 version = 2.0
operations = 5*(1 + 3 + 6 + 2) operations = 5*(1 + 3 + 6 + 2)
rounds = 80000 rounds = 90000
def test(self): def test(self):

View file

@ -8,7 +8,7 @@ from string import join
class ConcatUnicode(Test): class ConcatUnicode(Test):
version = 0.1 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 60000 rounds = 60000
@ -90,7 +90,7 @@ class ConcatUnicode(Test):
class CompareUnicode(Test): class CompareUnicode(Test):
version = 0.1 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 150000 rounds = 150000
@ -172,7 +172,7 @@ class CompareUnicode(Test):
class CreateUnicodeWithConcat(Test): class CreateUnicodeWithConcat(Test):
version = 0.1 version = 2.0
operations = 10 * 5 operations = 10 * 5
rounds = 80000 rounds = 80000
@ -247,9 +247,9 @@ class CreateUnicodeWithConcat(Test):
class UnicodeSlicing(Test): class UnicodeSlicing(Test):
version = 0.1 version = 2.0
operations = 5 * 7 operations = 5 * 7
rounds = 100000 rounds = 140000
def test(self): def test(self):
@ -308,7 +308,7 @@ class UnicodeSlicing(Test):
class UnicodeMappings(Test): class UnicodeMappings(Test):
version = 0.1 version = 2.0
operations = 3 * (5 + 4 + 2 + 1) operations = 3 * (5 + 4 + 2 + 1)
rounds = 10000 rounds = 10000
@ -381,9 +381,9 @@ class UnicodeMappings(Test):
class UnicodePredicates(Test): class UnicodePredicates(Test):
version = 0.1 version = 2.0
operations = 5 * 9 operations = 5 * 9
rounds = 100000 rounds = 120000
def test(self): def test(self):
@ -458,7 +458,7 @@ except ImportError:
else: else:
class UnicodeProperties(Test): class UnicodeProperties(Test):
version = 0.1 version = 2.0
operations = 5 * 8 operations = 5 * 8
rounds = 100000 rounds = 100000

44
Tools/pybench/clockres.py Normal file
View file

@ -0,0 +1,44 @@
#!/usr/bin/env python
""" clockres - calculates the resolution in seconds of a given timer.
Copyright (c) 2006, Marc-Andre Lemburg (mal@egenix.com). See the
documentation for further information on copyrights, or contact
the author. All Rights Reserved.
"""
import time
TEST_TIME = 1.0
def clockres(timer):
d = {}
wallclock = time.time
start = wallclock()
stop = wallclock() + TEST_TIME
spin_loops = range(1000)
while 1:
now = wallclock()
if now >= stop:
break
for i in spin_loops:
d[timer()] = 1
values = d.keys()
values.sort()
min_diff = TEST_TIME
for i in range(len(values) - 1):
diff = values[i+1] - values[i]
if diff < min_diff:
min_diff = diff
return min_diff
if __name__ == '__main__':
print 'Clock resolution of various timer implementations:'
print 'time.clock: %10.3fus' % (clockres(time.clock) * 1e6)
print 'time.time: %10.3fus' % (clockres(time.time) * 1e6)
try:
import systimes
print 'systimes.processtime: %10.3fus' % (clockres(systimes.processtime) * 1e6)
except ImportError:
pass

File diff suppressed because it is too large Load diff

View file

@ -16,7 +16,7 @@
platforms. platforms.
If no supported timing methods based on process time can be found, If no supported timing methods based on process time can be found,
the module reverts to the highest resolution wall-time timer the module reverts to the highest resolution wall-clock timer
instead. The system time part will then always be 0.0. instead. The system time part will then always be 0.0.
The module exports one public API: The module exports one public API:
@ -52,8 +52,8 @@ USE_CTYPES_GETPROCESSTIMES = 'cytpes GetProcessTimes() wrapper'
USE_WIN32PROCESS_GETPROCESSTIMES = 'win32process.GetProcessTimes()' USE_WIN32PROCESS_GETPROCESSTIMES = 'win32process.GetProcessTimes()'
USE_RESOURCE_GETRUSAGE = 'resource.getrusage()' USE_RESOURCE_GETRUSAGE = 'resource.getrusage()'
USE_PROCESS_TIME_CLOCK = 'time.clock() (process time)' USE_PROCESS_TIME_CLOCK = 'time.clock() (process time)'
USE_WALL_TIME_CLOCK = 'time.clock() (wall-time)' USE_WALL_TIME_CLOCK = 'time.clock() (wall-clock)'
USE_WALL_TIME_TIME = 'time.time() (wall-time)' USE_WALL_TIME_TIME = 'time.time() (wall-clock)'
if sys.platform[:3] == 'win': if sys.platform[:3] == 'win':
# Windows platform # Windows platform
@ -63,7 +63,7 @@ if sys.platform[:3] == 'win':
try: try:
import ctypes import ctypes
except ImportError: except ImportError:
# Use the wall-time implementation time.clock(), since this # Use the wall-clock implementation time.clock(), since this
# is the highest resolution clock available on Windows # is the highest resolution clock available on Windows
SYSTIMES_IMPLEMENTATION = USE_WALL_TIME_CLOCK SYSTIMES_IMPLEMENTATION = USE_WALL_TIME_CLOCK
else: else:
@ -91,7 +91,7 @@ if SYSTIMES_IMPLEMENTATION is None:
# time) # time)
SYSTIMES_IMPLEMENTATION = USE_PROCESS_TIME_CLOCK SYSTIMES_IMPLEMENTATION = USE_PROCESS_TIME_CLOCK
else: else:
# Use wall-time implementation time.time() since this provides # Use wall-clock implementation time.time() since this provides
# the highest resolution clock on most systems # the highest resolution clock on most systems
SYSTIMES_IMPLEMENTATION = USE_WALL_TIME_TIME SYSTIMES_IMPLEMENTATION = USE_WALL_TIME_TIME
@ -103,24 +103,27 @@ def getrusage_systimes():
def process_time_clock_systimes(): def process_time_clock_systimes():
return (time.clock(), 0.0) return (time.clock(), 0.0)
def wall_time_clock_systimes(): def wall_clock_clock_systimes():
return (time.clock(), 0.0) return (time.clock(), 0.0)
def wall_time_time_systimes(): def wall_clock_time_systimes():
return (time.time(), 0.0) return (time.time(), 0.0)
# Number of clock ticks per second for the values returned # Number of clock ticks per second for the values returned
# by GetProcessTimes() on Windows. # by GetProcessTimes() on Windows.
# #
# Note: Ticks returned by GetProcessTimes() are micro-seconds on # Note: Ticks returned by GetProcessTimes() are 100ns intervals on
# Windows XP (though the docs say 100ns intervals) # Windows XP. However, the process times are only updated with every
WIN32_PROCESS_TIMES_TICKS_PER_SECOND = 10e6 # clock tick and the frequency of these is somewhat lower: depending
# on the OS version between 10ms and 15ms. Even worse, the process
# time seems to be allocated to process currently running when the
# clock interrupt arrives, ie. it is possible that the current time
# slice gets accounted to a different process.
WIN32_PROCESS_TIMES_TICKS_PER_SECOND = 1e7
def win32process_getprocesstimes_systimes(): def win32process_getprocesstimes_systimes():
d = win32process.GetProcessTimes(win32process.GetCurrentProcess()) d = win32process.GetProcessTimes(win32process.GetCurrentProcess())
# Note: I'm not sure whether KernelTime on Windows is the same as
# system time on Unix - I've yet to see a non-zero value for
# KernelTime on Windows.
return (d['UserTime'] / WIN32_PROCESS_TIMES_TICKS_PER_SECOND, return (d['UserTime'] / WIN32_PROCESS_TIMES_TICKS_PER_SECOND,
d['KernelTime'] / WIN32_PROCESS_TIMES_TICKS_PER_SECOND) d['KernelTime'] / WIN32_PROCESS_TIMES_TICKS_PER_SECOND)
@ -149,10 +152,10 @@ elif SYSTIMES_IMPLEMENTATION is USE_PROCESS_TIME_CLOCK:
systimes = process_time_clock_systimes systimes = process_time_clock_systimes
elif SYSTIMES_IMPLEMENTATION is USE_WALL_TIME_CLOCK: elif SYSTIMES_IMPLEMENTATION is USE_WALL_TIME_CLOCK:
systimes = wall_time_clock_systimes systimes = wall_clock_clock_systimes
elif SYSTIMES_IMPLEMENTATION is USE_WALL_TIME_TIME: elif SYSTIMES_IMPLEMENTATION is USE_WALL_TIME_TIME:
systimes = wall_time_time_systimes systimes = wall_clock_time_systimes
elif SYSTIMES_IMPLEMENTATION is USE_WIN32PROCESS_GETPROCESSTIMES: elif SYSTIMES_IMPLEMENTATION is USE_WIN32PROCESS_GETPROCESSTIMES:
systimes = win32process_getprocesstimes_systimes systimes = win32process_getprocesstimes_systimes
@ -163,6 +166,17 @@ elif SYSTIMES_IMPLEMENTATION is USE_CTYPES_GETPROCESSTIMES:
else: else:
raise TypeError('no suitable systimes() implementation found') raise TypeError('no suitable systimes() implementation found')
def processtime():
""" Return the total time spent on the process.
This is the sum of user and system time as returned by
systimes().
"""
user, system = systimes()
return user + system
### Testing ### Testing
def some_workload(): def some_workload():