cython

Форк
0
/
ctuple.pyx 
299 строк · 6.4 Кб
1
# mode: run
2

3
import cython
4

5

6
def simple_convert(*o):
7
    """
8
    >>> simple_convert(1, 2)
9
    (1, 2.0)
10

11
    >>> simple_convert(1)
12
    Traceback (most recent call last):
13
    TypeError: Expected a sequence of size 2, got size 1
14
    >>> simple_convert(1, 2, 3)
15
    Traceback (most recent call last):
16
    TypeError: Expected a sequence of size 2, got size 3
17
    """
18
    cdef (int, double) xy = o
19
    return xy
20

21

22
def convert_from_list(*o):
23
    """
24
    >>> convert_from_list(1, 2)
25
    (1, 2.0)
26

27
    >>> convert_from_list(1)
28
    Traceback (most recent call last):
29
    TypeError: Expected a sequence of size 2, got size 1
30
    >>> convert_from_list(1, 2, 3)
31
    Traceback (most recent call last):
32
    TypeError: Expected a sequence of size 2, got size 3
33
    """
34
    cdef object values = list(o)
35
    cdef (int, double) xy = values
36
    return xy
37

38

39
def convert_from_deque(*o):
40
    """
41
    >>> convert_from_deque(1, 2)
42
    (1, 2.0)
43

44
    >>> convert_from_deque(1)
45
    Traceback (most recent call last):
46
    TypeError: Expected a sequence of size 2, got size 1
47
    >>> convert_from_deque(1, 2, 3)
48
    Traceback (most recent call last):
49
    TypeError: Expected a sequence of size 2, got size 3
50
    """
51
    from collections import deque
52
    cdef object values = deque(o)
53
    cdef (int, double) xy = values
54
    return xy
55

56

57
def indexing((int, double) xy):
58
    """
59
    >>> indexing((1, 2))
60
    (2, 3.0)
61
    """
62
    x = xy[0]
63
    y = xy[1]
64
    xy[0] = x + 1
65
    xy[1] = y + 1
66
    return xy
67

68
def unpacking((int, double) xy):
69
    """
70
    >>> unpacking((1, 2))
71
    (1, 2.0)
72
    """
73
    x, y = xy
74
    return x, y
75

76
cdef (int, double) side_effect((int, double) xy):
77
    print "called with", xy
78
    return xy
79

80
def unpacking_with_side_effect((int, double) xy):
81
    """
82
    >>> unpacking_with_side_effect((1, 2))
83
    called with (1, 2.0)
84
    (1, 2.0)
85
    """
86
    x, y = side_effect(xy)
87
    return x, y
88

89
def packing_tuple(int x, double y):
90
    """
91
    >>> packing_tuple(1, 2)
92
    (1, 2.0)
93
    """
94
    cdef (int, double) xy = (x, y)
95
    assert xy == (x, y), xy
96
    xy = (x, y) * 1
97
    assert xy == (x, y), xy
98
    xy = 1 * (x, y)
99
    return xy
100

101
def packing_list(int x, double y):
102
    """
103
    >>> packing_list(1, 2)
104
    (1, 2.0)
105
    """
106
    cdef (int, double) xy = [x, y]
107
    assert xy == (x, y), xy
108
    xy = [x, y] * 1
109
    assert xy == (x, y), xy
110
    xy = 1 * [x, y]
111
    return xy
112

113
def coerce_packing_tuple(int x, int y):
114
    cdef (int, double) xy = (x, y)
115
    """
116
    >>> coerce_packing_tuple(1, 2)
117
    (1, 2.0)
118
    """
119
    return xy
120

121
def c_types(int a, double b):
122
    """
123
    >>> c_types(1, 2)
124
    (1, 2.0)
125
    """
126
    cdef int* a_ptr
127
    cdef double* b_ptr
128
    cdef (int*, double*) ab = (&a, &b)
129
    a_ptr, b_ptr = ab
130
    return a_ptr[0], b_ptr[0]
131

132

133
cdef union Union:
134
    int x
135
    double y
136

137

138
def union_in_ctuple_literal():
139
    """
140
    >>> union_in_ctuple_literal()
141
    (1, 2.0)
142
    """
143
    cdef (Union,) a = ({"x": 1},)
144
    cdef (Union,) b = ({"y": 2},)
145
    return a[0].x, b[0].y
146

147

148
def union_in_ctuple_dynamic(*values):
149
    """
150
    >>> union_in_ctuple_dynamic(1, {'x': 1})
151
    1
152
    >>> union_in_ctuple_dynamic(2, {'y': 2})
153
    2.0
154
    >>> union_in_ctuple_dynamic(1, {'x': 1, 'y': 2})
155
    Traceback (most recent call last):
156
    ValueError: More than one union attribute passed: 'x' and 'y'
157
    """
158
    cdef (int, Union) a = values
159
    return a[1].x if a[0] == 1 else a[1].y
160

161

162
cdef (int, int*) cdef_ctuple_return_type(int x, int* x_ptr):
163
    return x, x_ptr
164

165
def call_cdef_ctuple_return_type(int x):
166
    """
167
    >>> call_cdef_ctuple_return_type(2)
168
    (2, 2)
169
    """
170
    cdef (int, int*) res = cdef_ctuple_return_type(x, &x)
171
    return res[0], res[1][0]
172

173

174
cpdef (int, double) cpdef_ctuple_return_type(int x, double y):
175
    """
176
    >>> cpdef_ctuple_return_type(1, 2)
177
    (1, 2.0)
178
    """
179
    return x, y
180

181

182
def cast_to_ctuple(*o):
183
    """
184
    >>> cast_to_ctuple(1, 2.)
185
    (1, 2.0)
186
    """
187
    cdef int x
188
    cdef double y
189
    x, y = <(int, double)>o
190
    return x, y
191

192

193
@cython.infer_types(True)
194
def test_type_inference():
195
    """
196
    >>> test_type_inference()
197
    """
198
    cdef int x = 1
199
    cdef double y = 2
200
    cdef object o = 3
201
    xy = (x, y)
202
    assert cython.typeof(xy) == "(int, double)", cython.typeof(xy)
203
    xo = (x, o)
204
    assert cython.typeof(xo) == "tuple object", cython.typeof(xo)
205

206

207
@cython.locals(a=(int,int), b=(cython.long,cython.float))
208
def test_pure_python_declaration(x, y):
209
    """
210
    >>> test_pure_python_declaration(1, 2)
211
    (int, int)
212
    (long, float)
213
    ((1, 2), (1, 2.0))
214
    >>> test_pure_python_declaration(1.0, 2.0)
215
    (int, int)
216
    (long, float)
217
    ((1, 2), (1, 2.0))
218
    >>> test_pure_python_declaration('x', 'y')
219
    Traceback (most recent call last):
220
    TypeError: an integer is required
221
    """
222
    a = (x, y)
223
    b = (x, y)
224
    print(cython.typeof(a))
225
    print(cython.typeof(b))
226
    return (a, b)
227

228

229
def test_equality((int, int) ab, (int, int) cd, (int, int) ef):
230
    """
231
    >>> test_equality((1, 2), (3, 4), (5, 6))
232
    True
233
    >>> test_equality((1, 2), (3, 4), (3, 4))
234
    True
235
    >>> test_equality((3, 4), (3, 4), (3, 4))
236
    False
237
    """
238
    return ab < cd <= ef
239

240
def test_equality_different_types((double, int) ab, (int, int) cd, (long, int) ef):
241
    """
242
    >>> test_equality((1, 2), (3, 4), (5, 6))
243
    True
244
    >>> test_equality((1, 2), (3, 4), (3, 4))
245
    True
246
    >>> test_equality((3, 4), (3, 4), (3, 4))
247
    False
248
    """
249
    return ab < cd <= ef
250

251
def test_binop((int, int) ab, (double, double) cd):
252
    """
253
    >>> test_binop((1, 2), (3, 4))
254
    (1, 2, 3.0, 4.0)
255
    """
256
    return ab + cd
257

258
def test_mul((int, int) ab, int c):
259
    """
260
    >>> test_mul((1, 2), 3)
261
    (1, 2, 1, 2, 1, 2)
262
    """
263
    return ab * c
264

265
def test_mul_to_ctuple((int, int) ab, int c):
266
    """
267
    >>> test_mul_to_ctuple((1, 2), 2)
268
    (1, 2, 1, 2)
269
    >>> test_mul_to_ctuple((1, 2), 3)
270
    Traceback (most recent call last):
271
    TypeError: Expected a sequence of size 4, got size 6
272
    """
273
    result: tuple[cython.int, cython.int, cython.int, cython.int] = ab * c
274
    return result
275

276
def test_unop((int, int) ab):
277
    """
278
    >>> test_unop((1, 2))
279
    True
280
    """
281
    return not ab
282

283
# This is testing both that fused ctuples work, and that
284
# different fused ctuples end up as separate types
285
cdef (cython.floating, cython.floating) two_fused(cython.floating x):
286
    return x, x
287

288
cdef (cython.floating, cython.floating, cython.floating) three_fused(cython.floating x):
289
    return x, x, x
290

291
def test_fused():
292
    """
293
    >>> a, b = test_fused()
294
    >>> a
295
    (1.0, 1.0)
296
    >>> b
297
    (2.0, 2.0, 2.0)
298
    """
299
    return two_fused(1.0), three_fused(2.0)
300

Использование cookies

Мы используем файлы cookie в соответствии с Политикой конфиденциальности и Политикой использования cookies.

Нажимая кнопку «Принимаю», Вы даете АО «СберТех» согласие на обработку Ваших персональных данных в целях совершенствования нашего веб-сайта и Сервиса GitVerse, а также повышения удобства их использования.

Запретить использование cookies Вы можете самостоятельно в настройках Вашего браузера.