Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
C
cython
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Labels
Merge Requests
0
Merge Requests
0
Analytics
Analytics
Repository
Value Stream
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Commits
Open sidebar
nexedi
cython
Commits
4e07fc52
Commit
4e07fc52
authored
Aug 21, 2012
by
Robert Bradshaw
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
More C++ class fixes, tests.
parent
3e25a388
Changes
7
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
140 additions
and
15 deletions
+140
-15
Cython/Compiler/ExprNodes.py
Cython/Compiler/ExprNodes.py
+3
-3
Cython/Compiler/ModuleNode.py
Cython/Compiler/ModuleNode.py
+2
-2
Cython/Compiler/Nodes.py
Cython/Compiler/Nodes.py
+7
-1
Cython/Compiler/Options.py
Cython/Compiler/Options.py
+1
-0
Cython/Compiler/PyrexTypes.py
Cython/Compiler/PyrexTypes.py
+13
-0
Cython/Compiler/Symtab.py
Cython/Compiler/Symtab.py
+21
-9
tests/run/cpp_classes_def.pyx
tests/run/cpp_classes_def.pyx
+93
-0
No files found.
Cython/Compiler/ExprNodes.py
View file @
4e07fc52
...
...
@@ -1329,9 +1329,8 @@ class NewExprNode(AtomicExprNode):
self
.
cpp_check
(
env
)
constructor
=
type
.
scope
.
lookup
(
u'<init>'
)
if
constructor
is
None
:
return_type
=
PyrexTypes
.
CFuncType
(
type
,
[],
exception_check
=
'+'
)
return_type
=
PyrexTypes
.
CPtrType
(
return_type
)
type
.
scope
.
declare_cfunction
(
u'<init>'
,
return_type
,
self
.
pos
)
func_type
=
PyrexTypes
.
CFuncType
(
type
,
[],
exception_check
=
'+'
)
type
.
scope
.
declare_cfunction
(
u'<init>'
,
func_type
,
self
.
pos
)
constructor
=
type
.
scope
.
lookup
(
u'<init>'
)
self
.
class_type
=
type
self
.
entry
=
constructor
...
...
@@ -3705,6 +3704,7 @@ class CallNode(ExprNode):
self
.
function
.
entry
=
constructor
self
.
function
.
set_cname
(
type
.
declaration_code
(
""
))
self
.
analyse_c_function_call
(
env
)
self
.
type
=
type
return
True
def
is_lvalue
(
self
):
...
...
Cython/Compiler/ModuleNode.py
View file @
4e07fc52
...
...
@@ -669,7 +669,7 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
def
generate_struct_union_predeclaration
(
self
,
entry
,
code
):
type
=
entry
.
type
if
type
.
is_cpp_class
and
type
.
templates
:
code
.
putln
(
"template <
class %s>"
%
", class
"
.
join
([
T
.
declaration_code
(
""
)
for
T
in
type
.
templates
]))
code
.
putln
(
"template <
typename %s>"
%
", typename
"
.
join
([
T
.
declaration_code
(
""
)
for
T
in
type
.
templates
]))
code
.
putln
(
self
.
sue_predeclaration
(
type
,
type
.
kind
,
type
.
cname
))
def
sue_header_footer
(
self
,
type
,
kind
,
name
):
...
...
@@ -728,7 +728,7 @@ class ModuleNode(Nodes.Node, Nodes.BlockNode):
code
.
put
(
" : public %s"
%
base_class_decl
)
code
.
putln
(
" {"
)
for
attr
in
scope
.
var_entries
:
if
attr
.
type
.
is_cfunction
:
if
attr
.
type
.
is_cfunction
and
attr
.
name
!=
"<init>"
:
code
.
put
(
"virtual "
)
code
.
putln
(
"%s;"
%
...
...
Cython/Compiler/Nodes.py
View file @
4e07fc52
...
...
@@ -1197,7 +1197,7 @@ class CppClassNode(CStructOrUnionDefNode, BlockNode):
if
self
.
entry
is
None
:
return
self
.
entry
.
is_cpp_class
=
1
scope
.
class_namespace
=
self
.
entry
.
type
.
declaration_code
(
""
)
scope
.
type
=
self
.
entry
.
type
defined_funcs
=
[]
if
self
.
attributes
is
not
None
:
if
self
.
in_pxd
and
not
env
.
in_cinclude
:
...
...
@@ -1206,6 +1206,8 @@ class CppClassNode(CStructOrUnionDefNode, BlockNode):
attr
.
analyse_declarations
(
scope
)
if
isinstance
(
attr
,
CFuncDefNode
):
defined_funcs
.
append
(
attr
)
if
self
.
templates
is
not
None
:
attr
.
template_declaration
=
"template <typename %s>"
%
", typename "
.
join
(
self
.
templates
)
self
.
body
=
StatListNode
(
self
.
pos
,
stats
=
defined_funcs
)
self
.
scope
=
scope
...
...
@@ -1935,6 +1937,7 @@ class CFuncDefNode(FuncDefNode):
# py_func wrapper for calling from Python
# overridable whether or not this is a cpdef function
# inline_in_pxd whether this is an inline function in a pxd file
# template_declaration String or None Used for c++ class methods
child_attrs
=
[
"base_type"
,
"declarator"
,
"body"
,
"py_func"
]
...
...
@@ -1943,6 +1946,7 @@ class CFuncDefNode(FuncDefNode):
directive_locals
=
None
directive_returns
=
None
override
=
None
template_declaration
=
None
def
unqualified_name
(
self
):
return
self
.
entry
.
name
...
...
@@ -2150,6 +2154,8 @@ class CFuncDefNode(FuncDefNode):
header
=
self
.
return_type
.
declaration_code
(
entity
,
dll_linkage
=
dll_linkage
)
#print (storage_class, modifiers, header)
if
self
.
template_declaration
:
code
.
putln
(
self
.
template_declaration
)
code
.
putln
(
"%s%s%s {"
%
(
storage_class
,
modifiers
,
header
))
def
generate_argument_declarations
(
self
,
env
,
code
):
...
...
Cython/Compiler/Options.py
View file @
4e07fc52
...
...
@@ -125,6 +125,7 @@ directive_defaults = {
# experimental, subject to change
'binding'
:
False
,
'experimental_cpp_class_def'
:
False
}
# Extra warning directives
...
...
Cython/Compiler/PyrexTypes.py
View file @
4e07fc52
...
...
@@ -1213,6 +1213,19 @@ class CVoidType(CType):
def
is_complete
(
self
):
return
0
class
InvisibleVoidType
(
CVoidType
):
#
# For use with C++ constructors and destructors return types.
# Acts like void, but does not print out a declaration.
#
def
declaration_code
(
self
,
entity_code
,
for_display
=
0
,
dll_linkage
=
None
,
pyrex
=
0
):
if
pyrex
or
for_display
:
base_code
=
"[void]"
else
:
base_code
=
public_decl
(
""
,
dll_linkage
)
return
self
.
base_declaration_code
(
base_code
,
entity_code
)
class
CNumericType
(
CType
):
#
...
...
Cython/Compiler/Symtab.py
View file @
4e07fc52
...
...
@@ -1995,7 +1995,7 @@ class CppClassScope(Scope):
is_cpp_class_scope
=
1
default_constructor
=
None
class_namespac
e
=
None
typ
e
=
None
def
__init__
(
self
,
name
,
outer_scope
,
templates
=
None
):
Scope
.
__init__
(
self
,
name
,
outer_scope
,
None
)
...
...
@@ -2010,15 +2010,21 @@ class CppClassScope(Scope):
def
declare_var
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'extern'
,
api
=
0
,
in_pxd
=
0
,
is_cdef
=
0
,
allow_pyobject
=
0
):
allow_pyobject
=
0
,
defining
=
0
):
# Add an entry for an attribute.
if
not
cname
:
cname
=
name
entry
=
self
.
declare
(
name
,
cname
,
type
,
pos
,
visibility
)
entry
=
self
.
lookup_here
(
name
)
if
defining
and
entry
is
not
None
:
if
not
entry
.
type
.
same_as
(
type
):
error
(
pos
,
"Function signature does not match previous declaration"
)
else
:
entry
=
self
.
declare
(
name
,
cname
,
type
,
pos
,
visibility
)
entry
.
is_variable
=
1
if
type
.
is_cfunction
and
self
.
class_namespace
:
entry
.
func_cname
=
"%s::%s"
%
(
self
.
class_namespace
,
cname
)
self
.
var_entries
.
append
(
entry
)
if
type
.
is_cfunction
and
self
.
type
:
entry
.
func_cname
=
"%s::%s"
%
(
self
.
type
.
declaration_code
(
""
),
cname
)
if
name
!=
"this"
and
(
defining
or
name
!=
"<init>"
):
self
.
var_entries
.
append
(
entry
)
if
type
.
is_pyobject
and
not
allow_pyobject
:
error
(
pos
,
"C++ class member cannot be a Python object"
)
...
...
@@ -2056,14 +2062,20 @@ class CppClassScope(Scope):
def
declare_cfunction
(
self
,
name
,
type
,
pos
,
cname
=
None
,
visibility
=
'extern'
,
api
=
0
,
in_pxd
=
0
,
defining
=
0
,
modifiers
=
(),
utility_code
=
None
):
if
name
==
self
.
name
.
split
(
'::'
)[
-
1
]
and
cname
is
None
:
if
name
in
(
self
.
name
.
split
(
'::'
)[
-
1
],
'__init__'
)
and
cname
is
None
:
self
.
check_base_default_constructor
(
pos
)
cname
=
self
.
type
.
cname
name
=
'<init>'
type
.
return_type
=
self
.
lookup
(
self
.
name
).
type
type
.
return_type
=
PyrexTypes
.
InvisibleVoidType
()
elif
name
==
'__dealloc__'
and
cname
is
None
:
cname
=
"~%s"
%
self
.
type
.
cname
name
=
'<del>'
type
.
return_type
=
PyrexTypes
.
InvisibleVoidType
()
prev_entry
=
self
.
lookup_here
(
name
)
entry
=
self
.
declare_var
(
name
,
type
,
pos
,
defining
=
defining
,
cname
=
cname
,
visibility
=
visibility
)
if
prev_entry
:
if
prev_entry
and
not
defining
:
entry
.
overloaded_alternatives
=
prev_entry
.
all_alternatives
()
entry
.
utility_code
=
utility_code
type
.
entry
=
entry
...
...
tests/run/cpp_classes_def.pyx
0 → 100644
View file @
4e07fc52
# cython: experimental_cpp_class_def=True
# tag: cpp
cdef
double
pi
from
math
import
pi
from
libc.math
cimport
sin
,
cos
cdef
extern
from
"shapes.h"
namespace
"shapes"
:
cdef
cppclass
Shape
:
float
area
()
cdef
cppclass
RegularPolygon
(
Shape
):
float
radius
# major
int
n
__init__
(
int
n
,
float
radius
):
this
.
n
=
n
this
.
radius
=
radius
float
area
():
cdef
double
theta
=
pi
/
this
.
n
return
this
.
radius
*
this
.
radius
*
sin
(
theta
)
*
cos
(
theta
)
*
this
.
n
def
test_Poly
(
int
n
,
float
radius
=
1
):
"""
>>> test_Poly(4)
2.0
>>> test_Poly(3)
1.299038052558899
>>> test_Poly(3, 10.0)
129.90380859375
>>> test_Poly(100)
3.139525890350342
>>> test_Poly(1000)
3.1415719985961914
"""
cdef
RegularPolygon
*
poly
try
:
poly
=
new
RegularPolygon
(
n
,
radius
)
poly
.
n
=
n
poly
.
radius
=
radius
return
poly
.
area
()
finally
:
del
poly
cdef
cppclass
InitDealloc
:
__init__
():
print
"Init"
__dealloc__
():
print
"Dealloc"
def
test_init_dealloc
():
"""
>>> test_init_dealloc()
start
Init
live
Dealloc
end
"""
print
"start"
cdef
InitDealloc
*
ptr
=
new
InitDealloc
()
print
"live"
del
ptr
print
"end"
cdef
cppclass
WithTemplate
[
T
]:
T
value
void
set_value
(
T
value
):
this
.
value
=
value
T
get_value
():
return
this
.
value
cdef
cppclass
ResolveTemplate
(
WithTemplate
[
long
]):
pass
def
test_templates
(
long
value
):
"""
>>> test_templates(10)
>>> test_templates(-2)
"""
cdef
WithTemplate
[
long
]
*
base
=
new
WithTemplate
[
long
]()
del
base
cdef
ResolveTemplate
*
resolved
=
new
ResolveTemplate
()
resolved
.
set_value
(
value
)
assert
resolved
.
value
==
resolved
.
get_value
()
==
value
,
resolved
.
value
base
=
resolved
base
.
set_value
(
2
*
value
)
assert
base
.
get_value
()
==
base
.
value
==
2
*
value
,
base
.
value
del
base
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment