source: git/factory/int_int.h @ 91695f

spielwiese
Last change on this file since 91695f was abddbe, checked in by Martin Lee <martinlee84@…>, 10 years ago
chg: added brief descriptions to some files
  • Property mode set to 100644
File size: 6.1 KB
Line 
1/* emacs edit mode for this file is -*- C++ -*- */
2
3#ifndef INCL_INT_INT_H
4#define INCL_INT_INT_H
5
6/**
7 * @file int_int.h
8 *
9 * Factory's internal integers
10**/
11
12// #include "config.h"
13
14#ifndef NOSTREAMIO
15#ifdef HAVE_IOSTREAM
16#include <iostream>
17#define OSTREAM std::ostream
18#elif defined(HAVE_IOSTREAM_H)
19#include <iostream.h>
20#define OSTREAM ostream
21#endif
22#endif /* NOSTREAMIO */
23
24#include "cf_assert.h"
25
26#include "int_cf.h"
27// #include <factory/cf_gmp.h>
28#include "gmpext.h"
29
30#ifdef HAVE_OMALLOC
31#ifndef OM_NDEBUG
32#define OM_NDEBUG
33#endif
34#  include <omalloc/omalloc.h>
35#endif
36
37/**
38 * factory's class for integers
39 *
40 * an integer is represented as an mpz_t thempi
41 *
42 * @sa InternalRational
43**/
44class InternalInteger : public InternalCF
45{
46private:
47    mpz_t thempi;
48
49    // auxilliary methods
50    inline InternalCF * normalizeMyself ();
51    inline InternalCF * uiNormalizeMyself ();
52
53    static inline InternalCF * normalizeMPI ( mpz_ptr );
54    static inline InternalCF * uiNormalizeMPI ( mpz_ptr );
55
56    static inline mpz_ptr MPI ( const InternalCF * const c );
57#ifdef HAVE_OMALLOC
58  static const omBin InternalInteger_bin;
59#endif
60public:
61#ifdef HAVE_OMALLOC
62  void* operator new(size_t)
63    {
64      void* addr;
65      omTypeAllocBin(void*, addr, InternalInteger_bin);
66      return addr;
67    }
68  void operator delete(void* addr, size_t)
69    {
70      omFreeBin(addr, InternalInteger_bin);
71    }
72#endif
73
74    InternalInteger();
75    InternalInteger( const InternalCF& )
76    {
77        ASSERT( 0, "ups there is something wrong in your code" );
78    }
79    InternalInteger( const int i );
80    InternalInteger( const long i );
81    InternalInteger( const char * str, const int base=10 );
82    InternalInteger( const mpz_ptr );
83    ~InternalInteger();
84    InternalCF* deepCopyObject() const;
85    const char * classname() const { return "InternalInteger"; }
86#ifndef NOSTREAMIO
87    void print( OSTREAM&, char* );
88#endif /* NOSTREAMIO */
89    InternalCF* genZero();
90    InternalCF* genOne();
91
92    bool is_imm() const;
93
94    int levelcoeff() const { return IntegerDomain; }
95    InternalCF* neg();
96
97    int comparesame( InternalCF* );
98
99    InternalCF* addsame( InternalCF* );
100    InternalCF* subsame( InternalCF* );
101    InternalCF* mulsame( InternalCF* );
102    InternalCF* dividesame( InternalCF* );
103    InternalCF* modulosame( InternalCF* );
104    InternalCF* divsame( InternalCF* );
105    InternalCF* modsame( InternalCF* );
106    void divremsame( InternalCF*, InternalCF*&, InternalCF*& );
107    bool divremsamet( InternalCF*, InternalCF*&, InternalCF*& );
108
109    int comparecoeff( InternalCF* );
110
111    InternalCF* addcoeff( InternalCF* );
112    InternalCF* subcoeff( InternalCF*, bool );
113    InternalCF* mulcoeff( InternalCF* );
114    InternalCF* dividecoeff( InternalCF*, bool );
115    InternalCF* modulocoeff( InternalCF*, bool );
116    InternalCF* divcoeff( InternalCF*, bool );
117    InternalCF* modcoeff( InternalCF*, bool );
118    void divremcoeff( InternalCF*, InternalCF*&, InternalCF*&, bool );
119    bool divremcoefft( InternalCF*, InternalCF*&, InternalCF*&, bool );
120
121    InternalCF * bgcdsame ( const InternalCF * const ) const;
122    InternalCF * bgcdcoeff ( const InternalCF * const );
123
124    InternalCF * bextgcdsame ( InternalCF *, CanonicalForm &, CanonicalForm & );
125    InternalCF * bextgcdcoeff ( InternalCF *, CanonicalForm &, CanonicalForm & );
126
127    long intval() const;
128
129    int intmod( int p ) const;
130
131    int sign() const;
132
133    InternalCF* sqrt();
134
135    int ilog2();
136
137    friend class InternalRational;
138    friend void gmp_numerator ( const CanonicalForm & f, mpz_ptr result);
139    friend void gmp_denominator ( const CanonicalForm & f, mpz_ptr result );
140    friend void getmpi ( InternalCF * value, mpz_t mpi);
141};
142
143/**
144 *
145 * normalizeMyself(), uiNormalizeMyself() - normalize CO.
146 *
147 * If CO fits into an immediate integer, delete CO and return the
148 * immediate.  Otherwise, return a pointer to CO.
149 *
150 * Note: We do not mind reference counting at this point!  CO is
151 * deleted unconditionally!
152 *
153**/
154inline InternalCF *
155InternalInteger::normalizeMyself ()
156{
157    ASSERT( getRefCount() == 1, "internal error: must not delete CO" );
158
159    if ( mpz_is_imm( thempi ) ) {
160        InternalCF * result = int2imm( mpz_get_si( thempi ) );
161        delete this;
162        return result;
163    } else
164        return this;
165}
166
167/**
168 * `uiNormalizeMyself()' is the same as `normalizeMyself()'
169 * except that CO is expected to be non-negative.  In this case,
170 * we may use `mpz_get_ui()' to convert the underlying mpi into
171 * an immediate which is slightly faster than the signed variant.
172 *
173 * Note: We do not mind reference counting at this point!  CO is
174 * deleted unconditionally!
175**/
176inline InternalCF *
177InternalInteger::uiNormalizeMyself ()
178{
179    ASSERT( getRefCount() == 1, "internal error: must not delete CO" );
180
181    if ( mpz_is_imm( thempi ) ) {
182        InternalCF * result = int2imm( mpz_get_ui( thempi ) );
183        delete this;
184        return result;
185    } else
186        return this;
187}
188
189/**
190 *
191 * normalizeMPI(), uiNormalizeMPI() - normalize a mpi.
192 *
193 * If `aMpi' fits into an immediate integer, clear `aMpi' and
194 * return the immediate.  Otherwise, return a new
195 * `InternalInteger' with `aMpi' as underlying mpi.
196 *
197**/
198inline InternalCF *
199InternalInteger::normalizeMPI ( mpz_ptr aMpi )
200{
201    if ( mpz_is_imm( aMpi ) ) {
202        InternalCF * result = int2imm( mpz_get_si( aMpi ) );
203        mpz_clear( aMpi );
204        return result;
205    } else
206        return new InternalInteger( aMpi );
207}
208
209/**
210 * `uiNormalizeMPI()' is the same as `normalizeMPI()' except that
211 * `aMpi' is expected to be non-begative.  In this case, we may
212 * use `mpz_get_ui()' to convert `aMpi' into an immediate which
213 * is slightly faster than the signed variant.
214**/
215inline InternalCF *
216InternalInteger::uiNormalizeMPI ( mpz_ptr aMpi )
217{
218    if ( mpz_is_imm( aMpi ) ) {
219        InternalCF * result = int2imm( mpz_get_ui( aMpi ) );
220        mpz_clear( aMpi );
221        return result;
222    } else
223        return new InternalInteger( aMpi );
224}
225
226/**
227 *
228 * MPI() - return underlying mpz_t of `c'.
229 *
230 * `c' is expected to be an `InternalInteger *'.  `c's underlying
231 * mpz_t is returned.
232 *
233**/
234inline mpz_ptr
235InternalInteger::MPI ( const InternalCF * const c )
236{
237    return (((InternalInteger*)c)->thempi);
238}
239
240#endif /* ! INCL_INT_INT_H */
Note: See TracBrowser for help on using the repository browser.