Loading...
Searching...
No Matches
integer.cpp
2#include <symengine/pow.h>
3#include <symengine/symengine_exception.h>
4#include <symengine/symengine_casts.h>
5
6namespace SymEngine
7{
8
9hash_t Integer::__hash__() const
10{
11 // only the least significant bits that fit into "long long int" are
12 // hashed:
13 return ((hash_t)mp_get_ui(this->i)) * (hash_t)(mp_sign(this->i));
14}
15
16bool Integer::__eq__(const Basic &o) const
17{
18 if (is_a<Integer>(o)) {
19 const Integer &s = down_cast<const Integer &>(o);
20 return this->i == s.i;
21 }
22 return false;
23}
24
25int Integer::compare(const Basic &o) const
26{
27 SYMENGINE_ASSERT(is_a<Integer>(o))
28 const Integer &s = down_cast<const Integer &>(o);
29 if (i == s.i)
30 return 0;
31 return i < s.i ? -1 : 1;
32}
33
34signed long int Integer::as_int() const
35{
36 // mp_get_si() returns "signed long int", so that's what we return from
37 // "as_int()" and we leave it to the user to do any possible further integer
38 // conversions.
39 if (not(mp_fits_slong_p(this->i))) {
40 throw SymEngineException("as_int: Integer larger than int");
41 }
42 return mp_get_si(this->i);
43}
44
45unsigned long int Integer::as_uint() const
46{
47 // mp_get_ui() returns "unsigned long int", so that's what we return from
48 // "as_uint()" and we leave it to the user to do any possible further
49 // integer
50 // conversions.
51 if (this->i < 0u) {
52 throw SymEngineException("as_uint: negative Integer");
53 }
54 if (not(mp_fits_ulong_p(this->i))) {
55 throw SymEngineException("as_uint: Integer larger than uint");
56 }
57 return mp_get_ui(this->i);
58}
59
60RCP<const Number> Integer::divint(const Integer &other) const
61{
62 if (other.i == 0) {
63 if (this->i == 0) {
64 return Nan;
65 } else {
66 return ComplexInf;
67 }
68 }
69 rational_class q(this->i, other.i);
70
71 // This is potentially slow, but has to be done, since q might not
72 // be in canonical form.
73 canonicalize(q);
74
76}
77
78RCP<const Number> Integer::rdiv(const Number &other) const
79{
80 if (is_a<Integer>(other)) {
81 if (this->i == 0) {
82 if (other.is_zero()) {
83 return Nan;
84 } else {
85 return ComplexInf;
86 }
87 }
88 rational_class q((down_cast<const Integer &>(other)).i, this->i);
89
90 // This is potentially slow, but has to be done, since q might not
91 // be in canonical form.
92 canonicalize(q);
93
95 } else {
96 throw NotImplementedError("Not Implemented");
97 }
98}
99
100RCP<const Number> Integer::pow_negint(const Integer &other) const
101{
102 RCP<const Number> tmp = powint(*other.neg());
103 if (is_a<Integer>(*tmp)) {
104 const integer_class &j = down_cast<const Integer &>(*tmp).i;
105#if SYMENGINE_INTEGER_CLASS == SYMENGINE_BOOSTMP
106 // boost::multiprecision::cpp_rational lacks an (int, cpp_int)
107 // constructor. must use cpp_rational(cpp_int,cpp_int)
108 rational_class q(integer_class(mp_sign(j)), mp_abs(j));
109#else
110 rational_class q(mp_sign(j), mp_abs(j));
111#endif
112 return Rational::from_mpq(std::move(q));
113 } else {
114 throw SymEngineException("powint returned non-integer");
115 }
116}
117
118RCP<const Integer> isqrt(const Integer &n)
119{
120 return integer(mp_sqrt(n.as_integer_class()));
121}
122
123RCP<const Integer> iabs(const Integer &n)
124{
125 return integer(mp_abs(n.as_integer_class()));
126}
127
128int i_nth_root(const Ptr<RCP<const Integer>> &r, const Integer &a,
129 unsigned long int n)
130{
131 if (n == 0)
132 throw SymEngineException("i_nth_root: Can not find Zeroth root");
133
134 int ret_val;
135 integer_class t;
136
137 ret_val = mp_root(t, a.as_integer_class(), n);
138 *r = integer(std::move(t));
139
140 return ret_val;
141}
142
144{
145 return mp_perfect_square_p(n.as_integer_class());
146}
147
148bool perfect_power(const Integer &n)
149{
150 return mp_perfect_power_p(n.as_integer_class());
151}
152
153} // namespace SymEngine
The lowest unit of symbolic representation.
Definition: basic.h:97
Integer Class.
Definition: integer.h:19
const integer_class & as_integer_class() const
Convert to integer_class.
Definition: integer.h:45
RCP< const Integer > neg() const
Definition: integer.h:116
unsigned long int as_uint() const
Convert to uint, raise an exception if it does not fit.
Definition: integer.cpp:45
RCP< const Number > powint(const Integer &other) const
Fast Power Evaluation.
Definition: integer.h:102
RCP< const Number > divint(const Integer &other) const
Integer Division.
Definition: integer.cpp:60
bool __eq__(const Basic &o) const override
Definition: integer.cpp:16
hash_t __hash__() const override
Definition: integer.cpp:9
int compare(const Basic &o) const override
Definition: integer.cpp:25
RCP< const Number > pow_negint(const Integer &other) const
Fast Negative Power Evaluation.
Definition: integer.cpp:100
signed long int as_int() const
Convert to int, raise an exception if it does not fit.
Definition: integer.cpp:34
integer_class i
i : object of integer_class
Definition: integer.h:22
virtual bool is_zero() const =0
static RCP< const Number > from_mpq(const rational_class &i)
Definition: rational.cpp:23
T move(T... args)
Main namespace for SymEngine package.
Definition: add.cpp:19
int i_nth_root(const Ptr< RCP< const Integer > > &r, const Integer &a, unsigned long int n)
Integer nth root.
Definition: integer.cpp:128
RCP< const Integer > isqrt(const Integer &n)
Integer Square root.
Definition: integer.cpp:118
bool perfect_square(const Integer &n)
Perfect Square.
Definition: integer.cpp:143
bool perfect_power(const Integer &n)
Perfect Square.
Definition: integer.cpp:148
std::enable_if< std::is_integral< T >::value, RCP< constInteger > >::type integer(T i)
Definition: integer.h:197
RCP< const Integer > iabs(const Integer &n)
Integer Absolute value.
Definition: integer.cpp:123