Commit 60c424d9 authored by Robert Bradshaw's avatar Robert Bradshaw

Use actual types in C++ conversion utility code.

parent 343064e8
......@@ -3330,58 +3330,26 @@ class CppClassType(CType):
if self.cname in builtin_cpp_conversions or self.cname in cpp_string_conversions:
X = "XYZABC"
tags = []
declarations = ["cdef extern from *:"]
context = {}
for ix, T in enumerate(self.templates or []):
if ix >= builtin_cpp_conversions[self.cname]:
break
if T.is_pyobject or not T.create_from_py_utility_code(env):
return False
tags.append(T.specialization_name())
if T.exception_value is not None:
# This is a hack due to the except value clause
# requiring a const (literal) value of the right
# (visible) type.
def guess_type(value):
if not T.is_typedef and (T.is_numeric or T.is_ptr):
return T
try:
int(value)
return c_longlong_type
except ValueError:
pass
try:
float(value)
return c_double_type
except ValueError:
pass
return T
except_type = guess_type(T.exception_value)
except_clause = "%s " % T.exception_value
if T.exception_check:
except_clause = "? %s" % except_clause
declarations.append(
" ctypedef %s %s '%s'" % (
except_type.declaration_code("", for_display=True), X[ix], T.empty_declaration_code()))
else:
except_clause = "*"
declarations.append(
" ctypedef struct %s '%s':\n pass" % (
X[ix], T.empty_declaration_code()))
declarations.append(
" cdef %s %s_from_py '%s' (object) except %s" % (
X[ix], X[ix], T.from_py_function, except_clause))
context[X[ix]] = T
if self.cname in cpp_string_conversions:
cls = 'string'
tags = type_identifier(self),
else:
cls = self.cname[5:]
cname = '__pyx_convert_%s_from_py_%s' % (cls, '__and_'.join(tags))
context = {
'template_type_declarations': '\n'.join(declarations),
context.update({
'cname': cname,
'maybe_unordered': self.maybe_unordered(),
'type': self.cname,
}
})
from .UtilityCode import CythonUtilityCode
env.use_utility_code(CythonUtilityCode.load(
cls.replace('unordered_', '') + ".from_py", "CppConvert.pyx", context=context))
......@@ -3394,19 +3362,15 @@ class CppClassType(CType):
if self.cname in builtin_cpp_conversions or self.cname in cpp_string_conversions:
X = "XYZABC"
tags = []
declarations = ["cdef extern from *:"]
context = {}
for ix, T in enumerate(self.templates or []):
if ix >= builtin_cpp_conversions[self.cname]:
break
if not T.create_to_py_utility_code(env):
return False
tags.append(T.specialization_name())
declarations.append(
" ctypedef struct %s '%s':\n pass" % (
X[ix], T.empty_declaration_code()))
declarations.append(
" cdef object %s_to_py '%s' (%s)" % (
X[ix], T.to_py_function, X[ix]))
context[X[ix]] = T
if self.cname in cpp_string_conversions:
cls = 'string'
prefix = 'PyObject_' # gets specialised by explicit type casts in CoerceToPyTypeNode
......@@ -3415,12 +3379,11 @@ class CppClassType(CType):
cls = self.cname[5:]
prefix = ''
cname = "__pyx_convert_%s%s_to_py_%s" % (prefix, cls, "____".join(tags))
context = {
'template_type_declarations': '\n'.join(declarations),
context.update({
'cname': cname,
'maybe_unordered': self.maybe_unordered(),
'type': self.cname,
}
})
from .UtilityCode import CythonUtilityCode
env.use_utility_code(CythonUtilityCode.load(
cls.replace('unordered_', '') + ".to_py", "CppConvert.pyx", context=context))
......
......@@ -37,8 +37,6 @@ cdef inline object {{cname.replace("PyObject", py_type, 1)}}(const string& s):
#################### vector.from_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass vector "std::vector" [T]:
void push_back(T&)
......@@ -47,14 +45,12 @@ cdef extern from *:
cdef vector[X] {{cname}}(object o) except *:
cdef vector[X] v
for item in o:
v.push_back(X_from_py(item))
v.push_back(<X>item)
return v
#################### vector.to_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass vector "const std::vector" [T]:
size_t size()
......@@ -62,13 +58,11 @@ cdef extern from *:
@cname("{{cname}}")
cdef object {{cname}}(vector[X]& v):
return [X_to_py(v[i]) for i in range(v.size())]
return [v[i] for i in range(v.size())]
#################### list.from_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass cpp_list "std::list" [T]:
void push_back(T&)
......@@ -77,7 +71,7 @@ cdef extern from *:
cdef cpp_list[X] {{cname}}(object o) except *:
cdef cpp_list[X] l
for item in o:
l.push_back(X_from_py(item))
l.push_back(<X>item)
return l
......@@ -85,8 +79,6 @@ cdef cpp_list[X] {{cname}}(object o) except *:
cimport cython
{{template_type_declarations}}
cdef extern from *:
cdef cppclass cpp_list "std::list" [T]:
cppclass const_iterator:
......@@ -101,15 +93,13 @@ cdef object {{cname}}(const cpp_list[X]& v):
o = []
cdef cpp_list[X].const_iterator iter = v.begin()
while iter != v.end():
o.append(X_to_py(cython.operator.dereference(iter)))
o.append(cython.operator.dereference(iter))
cython.operator.preincrement(iter)
return o
#################### set.from_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass set "std::{{maybe_unordered}}set" [T]:
void insert(T&)
......@@ -118,7 +108,7 @@ cdef extern from *:
cdef set[X] {{cname}}(object o) except *:
cdef set[X] s
for item in o:
s.insert(X_from_py(item))
s.insert(<X>item)
return s
......@@ -126,8 +116,6 @@ cdef set[X] {{cname}}(object o) except *:
cimport cython
{{template_type_declarations}}
cdef extern from *:
cdef cppclass cpp_set "std::{{maybe_unordered}}set" [T]:
cppclass const_iterator:
......@@ -142,14 +130,12 @@ cdef object {{cname}}(const cpp_set[X]& s):
o = set()
cdef cpp_set[X].const_iterator iter = s.begin()
while iter != s.end():
o.add(X_to_py(cython.operator.dereference(iter)))
o.add(cython.operator.dereference(iter))
cython.operator.preincrement(iter)
return o
#################### pair.from_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass pair "std::pair" [T, U]:
pair()
......@@ -158,13 +144,11 @@ cdef extern from *:
@cname("{{cname}}")
cdef pair[X,Y] {{cname}}(object o) except *:
x, y = o
return pair[X,Y](X_from_py(x), Y_from_py(y))
return pair[X,Y](<X>x, <Y>y)
#################### pair.to_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass pair "std::pair" [T, U]:
T first
......@@ -172,13 +156,11 @@ cdef extern from *:
@cname("{{cname}}")
cdef object {{cname}}(const pair[X,Y]& p):
return X_to_py(p.first), Y_to_py(p.second)
return p.first, p.second
#################### map.from_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass pair "std::pair" [T, U]:
pair(T&, U&)
......@@ -193,7 +175,7 @@ cdef map[X,Y] {{cname}}(object o) except *:
cdef dict d = o
cdef map[X,Y] m
for key, value in d.iteritems():
m.insert(pair[X,Y](X_from_py(key), Y_from_py(value)))
m.insert(pair[X,Y](<X>key, <Y>value))
return m
......@@ -203,8 +185,6 @@ cdef map[X,Y] {{cname}}(object o) except *:
cimport cython
{{template_type_declarations}}
cdef extern from *:
cdef cppclass map "std::{{maybe_unordered}}map" [T, U]:
cppclass value_type:
......@@ -224,15 +204,13 @@ cdef object {{cname}}(const map[X,Y]& s):
cdef map[X,Y].const_iterator iter = s.begin()
while iter != s.end():
key_value = &cython.operator.dereference(iter)
o[X_to_py(key_value.first)] = Y_to_py(key_value.second)
o[key_value.first] = key_value.second
cython.operator.preincrement(iter)
return o
#################### complex.from_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass std_complex "std::complex" [T]:
std_complex()
......@@ -246,8 +224,6 @@ cdef std_complex[X] {{cname}}(object o) except *:
#################### complex.to_py ####################
{{template_type_declarations}}
cdef extern from *:
cdef cppclass std_complex "std::complex" [T]:
X real()
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment