Commit 8da8ec52 authored by Robert Bradshaw's avatar Robert Bradshaw

cython.typeof special method

parent 578d94c5
...@@ -4245,6 +4245,24 @@ class SizeofVarNode(SizeofNode): ...@@ -4245,6 +4245,24 @@ class SizeofVarNode(SizeofNode):
def generate_result_code(self, code): def generate_result_code(self, code):
pass pass
class TypeofNode(StringNode):
# Compile-time type of an expression, as a string.
#
# operand ExprNode
subexprs = ['operand']
def analyse_types(self, env):
self.operand.analyse_types(env)
from StringEncoding import EncodedString
self.value = EncodedString(str(self.operand.type))
StringNode.analyse_types(self, env)
def analyse_as_type(self, env):
return None
def generate_evaluation_code(self, code):
self.generate_result_code(code)
#------------------------------------------------------------------- #-------------------------------------------------------------------
# #
...@@ -4850,9 +4868,6 @@ class CondExprNode(ExprNode): ...@@ -4850,9 +4868,6 @@ class CondExprNode(ExprNode):
def infer_type(self, env): def infer_type(self, env):
return self.compute_result_type(self.true_val.infer_type(env), return self.compute_result_type(self.true_val.infer_type(env),
self.false_val.infer_type(env)) self.false_val.infer_type(env))
def infer_types(self, env):
return self.compute_result_type(self.true_val.infer_types(env),
self.false_val.infer_types(env))
def calculate_constant_result(self): def calculate_constant_result(self):
if self.test.constant_result: if self.test.constant_result:
......
...@@ -328,7 +328,7 @@ class InterpretCompilerDirectives(CythonTransform, SkipDeclarations): ...@@ -328,7 +328,7 @@ class InterpretCompilerDirectives(CythonTransform, SkipDeclarations):
duplication of functionality has to occur: We manually track cimports duplication of functionality has to occur: We manually track cimports
and which names the "cython" module may have been imported to. and which names the "cython" module may have been imported to.
""" """
special_methods = set(['declare', 'union', 'struct', 'typedef', 'sizeof', 'cast', 'address', 'pointer', 'compiled', 'NULL']) special_methods = set(['declare', 'union', 'struct', 'typedef', 'sizeof', 'typeof', 'cast', 'address', 'pointer', 'compiled', 'NULL'])
def __init__(self, context, compilation_option_overrides): def __init__(self, context, compilation_option_overrides):
super(InterpretCompilerDirectives, self).__init__(context) super(InterpretCompilerDirectives, self).__init__(context)
...@@ -1009,6 +1009,11 @@ class TransformBuiltinMethods(EnvTransform): ...@@ -1009,6 +1009,11 @@ class TransformBuiltinMethods(EnvTransform):
node = SizeofTypeNode(node.function.pos, arg_type=type) node = SizeofTypeNode(node.function.pos, arg_type=type)
else: else:
node = SizeofVarNode(node.function.pos, operand=node.args[0]) node = SizeofVarNode(node.function.pos, operand=node.args[0])
elif function == 'typeof':
if len(node.args) != 1:
error(node.function.pos, u"sizeof takes exactly one argument" % function)
else:
node = TypeofNode(node.function.pos, operand=node.args[0])
elif function == 'address': elif function == 'address':
if len(node.args) != 1: if len(node.args) != 1:
error(node.function.pos, u"sizeof takes exactly one argument" % function) error(node.function.pos, u"sizeof takes exactly one argument" % function)
......
...@@ -30,6 +30,9 @@ def cast(type, arg): ...@@ -30,6 +30,9 @@ def cast(type, arg):
def sizeof(arg): def sizeof(arg):
return 1 return 1
def typeof(arg):
return type(arg)
def address(arg): def address(arg):
return pointer(type(arg))([arg]) return pointer(type(arg))([arg])
......
__doc__ = u"""
>>> simple()
int
long
long long
int *
int **
A
B
X
Python object
>>> expression()
double
double complex
int
unsigned int
"""
from cython cimport typeof
cdef class A:
pass
cdef class B(A):
pass
cdef struct X:
double a
double complex b
def simple():
cdef int i
cdef long l
cdef long long ll
cdef int* iptr
cdef int** iptrptr
cdef A a
cdef B b
cdef X x
print typeof(i)
print typeof(l)
print typeof(ll)
print typeof(iptr)
print typeof(iptrptr)
print typeof(a)
print typeof(b)
print typeof(x)
print typeof(None)
def expression():
cdef X x
cdef X *xptr
cdef short s
cdef int i
cdef unsigned int ui
print typeof(x.a)
print typeof(xptr.b)
print typeof(s + i)
print typeof(i + ui)
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