File: slice_ptr.pyx

package info (click to toggle)
cython 3.0.11%2Bdfsg-2
  • links: PTS, VCS
  • area: main
  • in suites: sid, trixie
  • size: 19,092 kB
  • sloc: python: 83,539; ansic: 18,831; cpp: 1,402; xml: 1,031; javascript: 511; makefile: 403; sh: 204; sed: 11
file content (73 lines) | stat: -rw-r--r-- 2,323 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
from libc.stdlib cimport malloc, free
from cpython.object cimport Py_EQ, Py_NE

def double_ptr_slice(x, L, int a, int b):
    """
    >>> L = list(range(10))
    >>> double_ptr_slice(5, L, 0, 10)
    >>> double_ptr_slice(6, L, 0, 10)
    >>> double_ptr_slice(None, L, 0, 10)
    >>> double_ptr_slice(0, L, 3, 7)
    >>> double_ptr_slice(5, L, 3, 7)
    >>> double_ptr_slice(9, L, 3, 7)

    >>> double_ptr_slice(EqualsEvens(), L, 0, 10)
    >>> double_ptr_slice(EqualsEvens(), L, 1, 10)
    """
    cdef double *L_c = NULL
    try:
        L_c = <double*>malloc(<unsigned long> len(L) * sizeof(double))
        for i, a in enumerate(L):
            L_c[i] = L[i]
        assert (x in L_c[:b]) == (x in L[:b])
        assert (x not in L_c[:b]) == (x not in L[:b])
        assert (x in L_c[a:b]) == (x in L[a:b])
        assert (x not in L_c[a:b]) == (x not in L[a:b])
        assert (x in L_c[a:b:2]) == (x in L[a:b:2])
        assert (x not in L_c[a:b:2]) == (x not in L[a:b:2])
    finally:
        free(L_c)

def void_ptr_slice(py_x, L, int a, int b):
    """
    >>> L = list(range(10))
    >>> void_ptr_slice(5, L, 0, 10)
    >>> void_ptr_slice(6, L, 0, 10)
    >>> void_ptr_slice(None, L, 0, 10)
    >>> void_ptr_slice(0, L, 3, 7)
    >>> void_ptr_slice(5, L, 3, 7)
    >>> void_ptr_slice(9, L, 3, 7)
    """
    # I'm using the fact that small Python ints are cached.
    cdef void **L_c = NULL
    cdef void *x = <void*>py_x
    try:
        L_c = <void**>malloc(<unsigned long> len(L) * sizeof(void*))
        for i, a in enumerate(L):
            L_c[i] = <void*>L[i]
        assert (x in L_c[:b]) == (py_x in L[:b])
        assert (x not in L_c[:b]) == (py_x not in L[:b])
        assert (x in L_c[a:b]) == (py_x in L[a:b])
        assert (x not in L_c[a:b]) == (py_x not in L[a:b])
        assert (x in L_c[a:b:2]) == (py_x in L[a:b:2])
        assert (x not in L_c[a:b:2]) == (py_x not in L[a:b:2])
    finally:
        free(L_c)

cdef class EqualsEvens:
    """
    >>> e = EqualsEvens()
    >>> e == 2
    True
    >>> e == 5
    False
    >>> [e == k for k in range(4)]
    [True, False, True, False]
    """
    def __richcmp__(self, other, int op):
        if op == Py_EQ:
            return other % 2 == 0
        elif op == Py_NE:
            return other % 2 == 1
        else:
            return False