Convert explicit template arguments to dummy arguments to try to make older gcc
[bigint/bigint.git] / NumberlikeArray.hh
CommitLineData
b35b6967
MM
1#ifndef NUMBERLIKEARRAY_H
2#define NUMBERLIKEARRAY_H
05780f4b 3
3e132790 4// Make sure we have NULL.
b3fe29df
MM
5#ifndef NULL
6#define NULL 0
7#endif
8
3e132790
MM
9/* A NumberlikeArray<Blk> object holds a heap-allocated array of Blk with a
10 * length and a capacity and provides basic memory management features.
11 * BigUnsigned and BigUnsignedInABase both subclass it.
6e1e0f2f 12 *
3e132790
MM
13 * NumberlikeArray provides no information hiding. Subclasses should use
14 * nonpublic inheritance and manually expose members as desired using
15 * declarations like this:
6e1e0f2f
MM
16 *
17 * public:
3e132790 18 * NumberlikeArray< the-type-argument >::getLength;
6e1e0f2f 19 */
05780f4b
MM
20template <class Blk>
21class NumberlikeArray {
2301f99c 22public:
5ff40cf5 23
3e132790
MM
24 // Type for the index of a block in the array
25 typedef unsigned int Index;
26 // The number of bits in a block, defined below.
27 static const unsigned int N;
28
29 // The current allocated capacity of this NumberlikeArray (in blocks)
30 Index cap;
31 // The actual length of the value stored in this NumberlikeArray (in blocks)
32 Index len;
33 // Heap-allocated array of the blocks (can be NULL if len == 0)
34 Blk *blk;
35
36 // Constructs a ``zero'' NumberlikeArray with the given capacity.
37 NumberlikeArray(Index c) : cap(c), len(0) {
a8b42b68 38 blk = (cap > 0) ? (new Blk[cap]) : NULL;
05780f4b 39 }
3e132790
MM
40
41 /* Constructs a zero NumberlikeArray without allocating a backing array.
42 * A subclass that doesn't know the needed capacity at initialization
43 * time can use this constructor and then overwrite blk without first
44 * deleting it. */
a8b42b68
MM
45 NumberlikeArray() : cap(0), len(0) {
46 blk = NULL;
05780f4b 47 }
3e132790
MM
48
49 // Destructor. Note that `delete NULL' is a no-op.
50 ~NumberlikeArray() {
51 delete [] blk;
05780f4b 52 }
5ff40cf5 53
3e132790
MM
54 /* Ensures that the array has at least the requested capacity; may
55 * destroy the contents. */
56 void allocate(Index c);
57
58 /* Ensures that the array has at least the requested capacity; does not
59 * destroy the contents. */
60 void allocateAndCopy(Index c);
61
62 // Copy constructor
63 NumberlikeArray(const NumberlikeArray<Blk> &x);
64
65 // Assignment operator
66 void operator=(const NumberlikeArray<Blk> &x);
5ff40cf5 67
3e132790
MM
68 // Constructor that copies from a given array of blocks
69 NumberlikeArray(const Blk *b, Index blen);
70
71 // ACCESSORS
72 Index getCapacity() const { return cap; }
73 Index getLength() const { return len; }
74 Blk getBlock(Index i) const { return blk[i]; }
75 bool isEmpty() const { return len == 0; }
76
77 /* Equality comparison: checks if both objects have the same length and
78 * equal (==) array elements to that length. Subclasses may wish to
79 * override. */
05780f4b 80 bool operator ==(const NumberlikeArray<Blk> &x) const;
5ff40cf5 81
3e132790
MM
82 bool operator !=(const NumberlikeArray<Blk> &x) const {
83 return !operator ==(x);
84 }
05780f4b
MM
85};
86
3e132790
MM
87/* BEGIN TEMPLATE DEFINITIONS. They are present here so that source files that
88 * include this header file can generate the necessary real definitions. */
05780f4b 89
2f145f11 90template <class Blk>
4efbb076 91const unsigned int NumberlikeArray<Blk>::N = 8 * sizeof(Blk);
2f145f11 92
05780f4b
MM
93template <class Blk>
94void NumberlikeArray<Blk>::allocate(Index c) {
95 // If the requested capacity is more than the current capacity...
96 if (c > cap) {
97 // Delete the old number array
a8b42b68 98 delete [] blk;
05780f4b
MM
99 // Allocate the new array
100 cap = c;
a8b42b68 101 blk = new Blk[cap];
05780f4b
MM
102 }
103}
104
05780f4b
MM
105template <class Blk>
106void NumberlikeArray<Blk>::allocateAndCopy(Index c) {
107 // If the requested capacity is more than the current capacity...
108 if (c > cap) {
a8b42b68 109 Blk *oldBlk = blk;
05780f4b
MM
110 // Allocate the new number array
111 cap = c;
a8b42b68 112 blk = new Blk[cap];
05780f4b
MM
113 // Copy number blocks
114 Index i;
115 for (i = 0; i < len; i++)
116 blk[i] = oldBlk[i];
117 // Delete the old array
118 delete [] oldBlk;
119 }
120}
121
05780f4b 122template <class Blk>
3e132790
MM
123NumberlikeArray<Blk>::NumberlikeArray(const NumberlikeArray<Blk> &x)
124 : len(x.len) {
05780f4b
MM
125 // Create array
126 cap = len;
a8b42b68 127 blk = new Blk[cap];
05780f4b
MM
128 // Copy blocks
129 Index i;
130 for (i = 0; i < len; i++)
131 blk[i] = x.blk[i];
132}
133
05780f4b
MM
134template <class Blk>
135void NumberlikeArray<Blk>::operator=(const NumberlikeArray<Blk> &x) {
3e132790
MM
136 /* Calls like a = a have no effect; catch them before the aliasing
137 * causes a problem */
05780f4b
MM
138 if (this == &x)
139 return;
140 // Copy length
141 len = x.len;
142 // Expand array if necessary
143 allocate(len);
144 // Copy number blocks
145 Index i;
146 for (i = 0; i < len; i++)
147 blk[i] = x.blk[i];
148}
149
05780f4b 150template <class Blk>
3e132790
MM
151NumberlikeArray<Blk>::NumberlikeArray(const Blk *b, Index blen)
152 : cap(blen), len(blen) {
05780f4b 153 // Create array
a8b42b68 154 blk = new Blk[cap];
05780f4b
MM
155 // Copy blocks
156 Index i;
157 for (i = 0; i < len; i++)
158 blk[i] = b[i];
159}
160
05780f4b
MM
161template <class Blk>
162bool NumberlikeArray<Blk>::operator ==(const NumberlikeArray<Blk> &x) const {
05780f4b 163 if (len != x.len)
3e132790 164 // Definitely unequal.
05780f4b
MM
165 return false;
166 else {
3e132790 167 // Compare corresponding blocks one by one.
05780f4b
MM
168 Index i;
169 for (i = 0; i < len; i++)
170 if (blk[i] != x.blk[i])
171 return false;
3e132790 172 // No blocks differed, so the objects are equal.
05780f4b
MM
173 return true;
174 }
175}
176
177#endif