[pypy-commit] pypy reflex-support: make benchmarking easier

wlav noreply at buildbot.pypy.org
Thu Jun 2 07:01:25 CEST 2011


Author: Wim Lavrijsen <WLavrijsen at lbl.gov>
Branch: reflex-support
Changeset: r44631:3ab12d3cad84
Date: 2011-05-31 16:01 -0700
http://bitbucket.org/pypy/pypy/changeset/3ab12d3cad84/

Log:	make benchmarking easier

diff --git a/pypy/module/cppyy/test/bench1.cxx b/pypy/module/cppyy/test/bench1.cxx
--- a/pypy/module/cppyy/test/bench1.cxx
+++ b/pypy/module/cppyy/test/bench1.cxx
@@ -1,45 +1,39 @@
 #include <iostream>
 #include <iomanip>
-#include <sys/times.h>
+#include <time.h>
 #include <unistd.h>
 
 #include "example01.h"
 
-static double gTicks = 0;
+static const int NNN = 10000000;
 
-double get_cputime() {
-   struct tms cpt;
-   times(&cpt);
-   return (double)(cpt.tms_utime+cpt.tms_stime) / gTicks;
-}
 
-int g() {
+int cpp_loop_offset() {
     int i = 0;
-    for ( ; i < 10000000; ++i)
+    for ( ; i < NNN*10; ++i)
         ;
     return i;
 }
 
-int f() {
+int cpp_bench1() {
     int i = 0;
     example01 e;
-    for ( ; i < 10000000; ++i)
+    for ( ; i < NNN*10; ++i)
         e.addDataToInt(i);
     return i;
 }
 
 
 int main() {
-    gTicks = (double)sysconf(_SC_CLK_TCK);
-    double t1 = get_cputime();
-    g();
-    double t2 = get_cputime();
-    f();
-    double t3 = get_cputime();
 
-    std::cout << std::setprecision( 8 );
-    std::cout << (t3 - t2) << " " << (t2 - t1) << std::endl;
-    std::cout << (t3-t2) - (t2 - t1) << std::endl;
+    clock_t t1 = clock();
+    cpp_loop_offset();
+    clock_t t2 = clock();
+    cpp_bench1();
+    clock_t t3 = clock();
+
+    std::cout << std::setprecision(8)
+              << ((t3-t2) - (t2-t1))/((double)CLOCKS_PER_SEC*10.) << std::endl;
 
     return 0;
 }
diff --git a/pypy/module/cppyy/test/bench1.py b/pypy/module/cppyy/test/bench1.py
--- a/pypy/module/cppyy/test/bench1.py
+++ b/pypy/module/cppyy/test/bench1.py
@@ -1,29 +1,112 @@
+import commands, os, sys, time
 
-import time
-import cppyy
-lib = cppyy.load_lib("./example01Dict.so")
-cls = cppyy._type_byname("example01")
-inst = cls.construct(0)
+NNN = 10000000
 
-def g():
-    res = 0
-    for i in range(10000000):
+
+def run_bench(bench):
+    global t_loop_offset
+
+    t1 = time.time()
+    bench()
+    t2 = time.time()
+
+    t_bench = (t2-t1)-t_loop_offset
+    return bench.scale*t_bench
+
+def print_bench(name, t_bench):
+    global t_cppref
+    print ':::: %s cost: %#6.3fs (%#4dx)' % (name, t_bench, t_bench/t_cppref)
+
+def python_loop_offset():
+    for i in range(NNN):
         i
+    return i
 
-addDataToInt = cls.get_overload("addDataToInt")
+class PyCintexBench1(object):
+    scale = 10
+    def __init__(self):
+        import PyCintex
+        self.lib = PyCintex.gbl.gSystem.Load("./example01Dict.so")
 
-def f():
-    res = 0
-    for i in range(10000000):
-        #inst.invoke(cls.get_overload("addDataToDouble"), float(i))
-        #inst.invoke(cls.get_overload("addDataToInt"), i)
-        inst.invoke(addDataToInt, i)
+        self.cls   = PyCintex.gbl.example01
+        self.inst  = self.cls(0)
+        self.scale = 10
 
-g(); f();
-t1 = time.time()
-g()
-t2 = time.time()
-f()
-t3 = time.time()
-print t3 - t2, t2 - t1
-print (t3 - t2) - (t2 - t1)
+    def __call__(self):
+        instance = self.inst
+        niter = NNN/self.scale
+        for i in range(niter):
+            instance.addDataToInt(i)
+        return i
+
+class CppyyInterpBench1(object):
+    scale = 1
+    def __init__(self):
+        import cppyy
+        self.lib = cppyy.load_lib("./example01Dict.so")
+
+        self.cls  = cppyy._type_byname("example01")
+        self.inst = self.cls.construct(0)
+
+    def __call__(self):
+        addDataToInt = self.cls.get_overload("addDataToInt")
+        instance = self.inst
+        for i in range(NNN):
+            #inst.invoke(cls.get_overload("addDataToDouble"), float(i))
+            #inst.invoke(cls.get_overload("addDataToInt"), i)
+            instance.invoke(addDataToInt, i)
+        return i
+
+class CppyyPythonBench1(object):
+    scale = 1
+    def __init__(self):
+        import cppyy
+        self.lib = cppyy.load_lib("./example01Dict.so")
+
+        self.cls = cppyy.gbl.example01
+        self.inst = self.cls(0)
+
+    def __call__(self):
+        instance = self.inst
+        for i in range(NNN):
+            instance.addDataToInt(i)
+        return i
+
+
+if __name__ == '__main__':
+    python_loop_offset();
+
+    # time python loop offset
+    t1 = time.time()
+    python_loop_offset()
+    t2 = time.time()
+    t_loop_offset = t2-t1
+
+    # special case for PyCintex (run under python, not pypy-c)
+    if '--pycintex' in sys.argv:
+        cintex_bench1 = PyCintexBench1()
+        print run_bench(cintex_bench1)
+        sys.exit(0)
+
+    # get C++ reference point
+    if not os.path.exists("bench1.exe") or\
+            os.stat("bench1.exe").st_mtime < os.stat("bench1.cxx").st_mtime:
+        print "rebuilding bench1.exe ... "
+        os.system( "g++ -O2 bench1.cxx example01.cxx -o bench1.exe" )
+    stat, cppref = commands.getstatusoutput("./bench1.exe")
+    t_cppref = float(cppref)
+
+    # warm-up
+    print "warming up ... "
+    interp_bench1 = CppyyInterpBench1()
+    python_bench1 = CppyyPythonBench1()
+    interp_bench1(); python_bench1()
+
+    # to allow some consistency checking
+    print "C++ reference uses %.3fs" % t_cppref
+
+    # test runs ...
+    print_bench("cppyy interp", run_bench(interp_bench1))
+    print_bench("cppyy python", run_bench(python_bench1))
+    stat, t_cintex = commands.getstatusoutput("python bench1.py --pycintex")
+    print_bench("pycintex    ", float(t_cintex))
diff --git a/pypy/module/cppyy/test/example01.cxx b/pypy/module/cppyy/test/example01.cxx
--- a/pypy/module/cppyy/test/example01.cxx
+++ b/pypy/module/cppyy/test/example01.cxx
@@ -20,11 +20,9 @@
 }
 example01::example01(int a) : m_somedata(a) {
     count++;
-    std::cout << "constructor called" << std::endl;
 }
 example01::example01(const example01& e) : m_somedata(e.m_somedata) {
     count++;
-    std::cout << "copy constructor called" << std::endl;
 }
 example01& example01::operator=(const example01& e) {
     if (this != &e) {


More information about the pypy-commit mailing list