1# mode: run
2# tag: cpp, werror, cpp11
3
4import sys
5from libcpp.map cimport map
6from libcpp.unordered_map cimport unordered_map
7from libcpp.set cimport set as cpp_set
8from libcpp.unordered_set cimport unordered_set
9from libcpp.string cimport string
10from libcpp.pair cimport pair
11from libcpp.vector cimport vector
12from libcpp.list cimport list as cpp_list
13
14py_set = set
15py_xrange = xrange
16py_unicode = unicode
17
18cdef string add_strings(string a, string b):
19    return a + b
20
21def normalize(bytes b):
22    if sys.version_info[0] >= 3:
23        return b.decode("ascii")
24    else:
25        return b
26
27def test_string(o):
28    """
29    >>> normalize(test_string("abc".encode('ascii')))
30    'abc'
31    >>> normalize(test_string("abc\\x00def".encode('ascii')))
32    'abc\\x00def'
33    """
34    cdef string s = o
35    return s
36
37def test_encode_to_string(o):
38    """
39    >>> normalize(test_encode_to_string('abc'))
40    'abc'
41    >>> normalize(test_encode_to_string('abc\\x00def'))
42    'abc\\x00def'
43    """
44    cdef string s = o.encode('ascii')
45    return s
46
47def test_encode_to_string_cast(o):
48    """
49    >>> normalize(test_encode_to_string_cast('abc'))
50    'abc'
51    >>> normalize(test_encode_to_string_cast('abc\\x00def'))
52    'abc\\x00def'
53    """
54    s = <string>o.encode('ascii')
55    return s
56
57def test_unicode_encode_to_string(unicode o):
58    """
59    >>> normalize(test_unicode_encode_to_string(py_unicode('abc')))
60    'abc'
61    >>> normalize(test_unicode_encode_to_string(py_unicode('abc\\x00def')))
62    'abc\\x00def'
63    """
64    cdef string s = o.encode('ascii')
65    return s
66
67def test_string_call(a, b):
68    """
69    >>> normalize(test_string_call("abc".encode('ascii'), "xyz".encode('ascii')))
70    'abcxyz'
71    """
72    return add_strings(a, b)
73
74def test_c_string_convert(char *c_string):
75    """
76    >>> normalize(test_c_string_convert("abc".encode('ascii')))
77    'abc'
78    """
79    cdef string s
80    with nogil:
81        s = c_string
82    return s
83
84def test_int_vector(o):
85    """
86    >>> test_int_vector([1, 2, 3])
87    [1, 2, 3]
88    >>> test_int_vector((1, 10, 100))
89    [1, 10, 100]
90    >>> test_int_vector(py_xrange(1,10,2))
91    [1, 3, 5, 7, 9]
92    >>> test_int_vector([10**20])       #doctest: +ELLIPSIS
93    Traceback (most recent call last):
94    ...
95    OverflowError: ...
96    """
97    cdef vector[int] v = o
98    return v
99
100def test_string_vector(s):
101    """
102    >>> list(map(normalize, test_string_vector('ab cd ef gh'.encode('ascii'))))
103    ['ab', 'cd', 'ef', 'gh']
104    """
105    cdef vector[string] cpp_strings = s.split()
106    return cpp_strings
107
108cdef list convert_string_vector(vector[string] vect):
109    return vect
110
111def test_string_vector_temp_funcarg(s):
112    """
113    >>> list(map(normalize, test_string_vector_temp_funcarg('ab cd ef gh'.encode('ascii'))))
114    ['ab', 'cd', 'ef', 'gh']
115    """
116    return convert_string_vector(s.split())
117
118def test_double_vector(o):
119    """
120    >>> test_double_vector([1, 2, 3])
121    [1.0, 2.0, 3.0]
122    >>> test_double_vector([10**20])
123    [1e+20]
124    """
125    cdef vector[double] v = o
126    return v
127
128def test_repeated_double_vector(a, b, int n):
129    """
130    >>> test_repeated_double_vector(1, 1.5, 3)
131    [1.0, 1.5, 1.0, 1.5, 1.0, 1.5]
132    """
133    cdef vector[double] v = [a, b] * n
134    return v
135
136ctypedef int my_int
137
138def test_typedef_vector(o):
139    """
140    >>> test_typedef_vector([1, 2, 3])
141    [1, 2, 3]
142    >>> test_typedef_vector([1, 2, 3**100])       #doctest: +ELLIPSIS
143    Traceback (most recent call last):
144    ...
145    OverflowError: ...
146    >>> test_typedef_vector([1, 2, None])       #doctest: +ELLIPSIS
147    Traceback (most recent call last):
148    ...
149    TypeError: an integer is required
150    """
151    cdef vector[my_int] v = o
152    return v
153
154def test_pair(o):
155    """
156    >>> test_pair((1, 2))
157    (1, 2.0)
158    """
159    cdef pair[long, double] p = o
160    return p
161
162def test_list(o):
163    """
164    >>> test_list([1, 2, 3])
165    [1, 2, 3]
166    """
167    cdef cpp_list[int] l = o
168    return l
169
170def test_set(o):
171    """
172    >>> sorted(test_set([1, 2, 3]))
173    [1, 2, 3]
174    >>> sorted(test_set([1, 2, 3, 3]))
175    [1, 2, 3]
176    >>> type(test_set([])) is py_set
177    True
178    """
179    cdef cpp_set[long] s = o
180    return s
181
182def test_unordered_set(o):
183   """
184   >>> sorted(test_unordered_set([1, 2, 3]))
185   [1, 2, 3]
186   >>> sorted(test_unordered_set([1, 2, 3, 3]))
187   [1, 2, 3]
188   >>> type(test_unordered_set([])) is py_set
189   True
190   """
191   cdef unordered_set[long] s = o
192   return s
193
194def test_map(o):
195    """
196    >>> test_map({1: 1.0, 2: 0.5, 3: 0.25})
197    {1: 1.0, 2: 0.5, 3: 0.25}
198    """
199    cdef map[int, double] m = o
200    return m
201
202def test_unordered_map(o):
203   """
204   >>> d = test_map({1: 1.0, 2: 0.5, 3: 0.25})
205   >>> sorted(d)
206   [1, 2, 3]
207   >>> (d[1], d[2], d[3])
208   (1.0, 0.5, 0.25)
209   """
210   cdef unordered_map[int, double] m = o
211   return m
212
213def test_nested(o):
214    """
215    >>> test_nested({})
216    {}
217    >>> d = test_nested({(1.0, 2.0): [1, 2, 3], (1.0, 0.5): [1, 10, 100]})
218    >>> type(d) is dict or type(d)
219    True
220    >>> sorted(d)
221    [(1.0, 0.5), (1.0, 2.0)]
222    >>> d[(1.0, 0.5)]
223    [1, 10, 100]
224    >>> d[(1.0, 2.0)]
225    [1, 2, 3]
226    """
227    cdef map[pair[double, double], vector[int]] m = o
228    return m
229
230cpdef enum Color:
231    RED = 0
232    GREEN
233    BLUE
234
235def test_enum_map(o):
236    """
237    >>> test_enum_map({RED: GREEN})
238    {0: 1}
239    """
240    cdef map[Color, Color] m = o
241    return m
242