1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104
|
# C:\home\eric\wrk\scipy\weave\examples>python functional.py
# desired: [2, 3, 4]
# actual: [2, 3, 4]
# actual2: [2, 3, 4]
# python speed: 0.039999961853
# SCXX speed: 0.0599999427795
# speed up: 0.666666666667
# c speed: 0.0200001001358
# speed up: 1.99998807913
from __future__ import absolute_import, print_function
import sys
sys.path.insert(0,'..')
import inline_tools
from types import *
def c_list_map(func,seq):
""" Uses CXX C code to implement a simple map-like function.
It does not provide any error checking.
"""
assert(type(func) in [FunctionType,MethodType,type(len)])
code = """
#line 22 "functional.py"
py::tuple args(1);
int N = seq.len();
py::list result(N);
for(int i = 0; i < N;i++)
{
args[0] = seq[i];
result[i] = func.call(args);
}
return_val = result;
"""
return inline_tools.inline(code,['func','seq'])
def c_list_map2(func,seq):
""" Uses Python API more than CXX to implement a simple map-like function.
It does not provide any error checking.
"""
assert(type(func) in [FunctionType,MethodType,type(len)])
code = """
#line 40 "functional.py"
py::tuple args(1);
PyObject* py_args = (PyObject*)args;
py::list result(seq.len());
PyObject* py_result = (PyObject*)result;
PyObject* item = NULL;
PyObject* this_result = NULL;
int N = seq.len();
for(int i = 0; i < N;i++)
{
item = PyList_GET_ITEM(py_seq,i);
Py_INCREF(item);
PyTuple_SetItem(py_args,0,item);
this_result = PyEval_CallObject(py_func,py_args);
PyList_SetItem(py_result,i,this_result);
}
return_val = result;
"""
return inline_tools.inline(code,['func','seq'])
def main():
seq = ['aa','bbb','cccc']
print('desired:', map(len,seq))
print('actual:', c_list_map(len,seq))
print('actual2:', c_list_map2(len,seq))
def time_it(m,n):
import time
seq = ['aadasdf'] * n
t1 = time.time()
for i in range(m):
result = map(len,seq)
t2 = time.time()
py = t2 - t1
print('python speed:', py)
#load cache
result = c_list_map(len,seq)
t1 = time.time()
for i in range(m):
result = c_list_map(len,seq)
t2 = time.time()
c = t2-t1
print('SCXX speed:', c)
print('speed up:', py / c)
#load cache
result = c_list_map2(len,seq)
t1 = time.time()
for i in range(m):
result = c_list_map2(len,seq)
t2 = time.time()
c = t2-t1
print('c speed:', c)
print('speed up:', py / c)
if __name__ == "__main__":
main()
time_it(100,1000)
|