Statistiques
| Révision :

root / pobysoPythonSage / src / sageMpfr.spyx @ 269

Historique | Voir | Annoter | Télécharger (5,13 ko)

1
#cimport cython 
2
from libc.stdlib          cimport malloc,free
3
from sage.rings.real_mpfr cimport *
4
from sage.rings.real_mpfi cimport *
5
#
6
# Functions to manipulate the real RealNumber values.
7
#
8
# Import constants and declarations that are not exported
9
# from the Sage real_mpfr.pyx file.
10
# Notes:
11
# - notice how #define constants are imported.
12
# - before mpfr_min_prec() is declared, we need to "ctypedef" mpfr_prec_t
13
#   if we want to be consistent with MPFR notations. The actual type comes 
14
#   from mpfr.h but, according to documentation, any type of same general 
15
#   kind would have been OK.
16
cdef extern from "mpfr.h":
17
    ctypedef unsigned short mpfr_prec_t
18
    cdef mpfr_prec_t MPFR_PREC_MIN "MPFR_PREC_MIN"
19
    cdef mpfr_rnd_t MPFR_RNDN "MPFR_RNDN"
20
    cdef mpfr_prec_t mpfr_min_prec(mpfr_t x)
21

    
22
cpdef unsigned long int deref(unsigned long int p, int index):
23
    return((<unsigned long int*>p)[index])
24

    
25
cpdef unsigned long int get_interval_value(RealIntervalFieldElement x):
26
    """
27
    Get the address of the value of a RealIntervalField Element. 
28
    This address can be used to to set the value as well.
29
    """
30
    return(<unsigned long int>&(x.value))
31

    
32
cpdef unsigned long int get_rn_value(RealNumber x):
33
    """
34
    Get the address of the value of a RealNumber. This address can be
35
    used to to set the value as well.
36
    """
37
    return(<unsigned long int>(&(x.value)))
38
    
39
cpdef set_interval_value(RealIntervalFieldElement x, unsigned long int p):
40
    """
41
    Set the value of x from MPFI interval p.
42
    """
43
    # We use the "array trick" to workaround the pointer dereferencing
44
    # issue (in Cython there is no unary operator "*").
45
    #
46
    mpfi_set(x.value, (<mpfi_t *>p)[0])
47

    
48
cpdef set_rn_value(RealNumber x, unsigned long int p, mpfr_rnd_t rnd=MPFR_RNDN):
49
    """
50
    Set the value of x from MPFR number p.
51
    """
52
    # We use the "array trick" to workaround the pointer dereferencing
53
    # issue (in Cython there is no unary operator "*").
54
    mpfr_set(x.value, (<mpfr_t *>p)[0], rnd)
55
#
56
cpdef mpfr_prec_t min_rn_size(RealNumber x):
57
    """
58
    Compute the minimum number of bits necessary to represent
59
    the x Sage RealNumber's value.
60
    If x is a power of 2 (only 1 bit needed) return the MPFR
61
    MPFR_PREC_MIN value.
62
    """
63
    cdef mpfr_prec_t min_prec = mpfr_min_prec(x.value) 
64
    if min_prec < MPFR_PREC_MIN:
65
        return(MPFR_PREC_MIN)
66
    else:
67
        return(min_prec)
68
#
69
cpdef min_mpfr_size(unsigned long int p):
70
    """
71
    Compute the minimum number of bits necessary to represent
72
    the MPFR value pointed by the mpfr_t pointer p (hence the int type).
73
    If *p is a power of 2 (only 1 bit needed) return the MPFR
74
    MPFR_PREC_MIN value.
75
    """
76
    # We use the "array trick" to workaround the pointer dereferencing
77
    # issue (in Cython there is no unary operator "*").
78
    cdef mpfr_prec_t min_prec = mpfr_min_prec((<mpfr_t *>p)[0]) 
79
    if min_prec < MPFR_PREC_MIN:
80
        return(MPFR_PREC_MIN)
81
    else:
82
        return(min_prec)
83

    
84
cpdef free_mpfi_num(unsigned long int mpfiNum):
85
    """
86
    Free a MPFI interval pointed by mpfiNum (hece the unsigned long int type).
87
    """
88
    # We use the "array trick" to workaround the pointer dereferencing
89
    # issue (in Cython there is no unary operator "*").
90
    mpfi_clear((<mpfi_t*>mpfiNum)[0])
91

    
92
cpdef free_mpfr_num(unsigned long int mpfrNum):
93
    """
94
    Free a MPFR number pointed by mpfrNum (hece the int type).
95
    """
96
    # We use the "array trick" to workaround the pointer dereferencing
97
    # issue (in Cython there is no unary operator "*").
98
    mpfr_clear((<mpfr_t*>mpfrNum)[0])
99

    
100
cpdef unsigned long int new_interval_num(unsigned int prec):
101
    """
102
    Create a newly allocated MPFI interval to precision prec.
103
    """
104
    cdef mpfi_t *newValue = NULL
105
    print "Precision : ", prec
106
    newValue = <mpfi_t*>malloc(sizeof(mpfi_t))
107
    mpfi_init2(newValue[0], prec)
108
    print "Creation done!"
109
    return(<unsigned long int>newValue)
110

    
111
cpdef unsigned long int new_mpfr_num(unsigned int prec):
112
    cdef mpfr_t *newValue = NULL
113
    print "Precision : ", prec
114
    newValue = <mpfr_t*>malloc(sizeof(mpfr_t))
115
    mpfr_init2(newValue[0], prec)
116
    print "Creation done!"
117
    return(<unsigned long int>newValue)
118

    
119
#
120

    
121
cpdef cmp_interval_values(RealIntervalFieldElement x, 
122
                         RealIntervalFieldElement y):
123
    """
124
    Compare two intervals with the mpfi_cmp function
125
    """
126
    return(mpfi_cmp(x.value, y.value))
127
 
128
cpdef cmp_rn_values(RealNumber x, RealNumber y):
129
    """
130
    Compare two RN with the mpfr_cmp function
131
    """
132
    return(mpfr_cmp(x.value, y.value))
133
 
134
# Do not use this function!
135
# It changes the precision of the instance behind the curtain, but precision is
136
# class attribute. If the precision is increased, memory space is wasted and
137
# other problems may surface in subsequent operations.
138
# If the precision is decreased the semantics
139
# are broken since the expected precision (from the class attribute) is not
140
# the actual precision.
141
#
142
cpdef s_rn_value(RealNumber x, unsigned long int p):
143
    mpfr_clear(x.value)
144
    mpfr_init2(x.value, mpfr_get_prec((<mpfr_t *>p)[0]))
145
    #x.__prec = mpfr_get_prec(x.value)
146
    printf("x.value prec: %d\n", mpfr_get_prec(x.value))
147
    mpfr_set(x.value, (<mpfr_t *>p)[0], GMP_RNDN)