1 |
cycrow |
1 |
#ifndef EXT_ARRAY_INCLUDED
|
|
|
2 |
#define EXT_ARRAY_INCLUDED
|
|
|
3 |
|
|
|
4 |
#include <memory.h>
|
|
|
5 |
|
|
|
6 |
namespace ext
|
|
|
7 |
{
|
|
|
8 |
|
|
|
9 |
template <class Ty>
|
|
|
10 |
class array
|
|
|
11 |
{
|
|
|
12 |
public:
|
|
|
13 |
typedef size_t size_type;
|
|
|
14 |
typedef Ty value_type;
|
|
|
15 |
typedef Ty* value_type_ptr;
|
|
|
16 |
typedef Ty& reference;
|
|
|
17 |
typedef const Ty& const_reference;
|
|
|
18 |
typedef int difference_type;
|
|
|
19 |
|
|
|
20 |
class const_iterator
|
|
|
21 |
{
|
|
|
22 |
protected:
|
|
|
23 |
value_type *m_ptr;
|
|
|
24 |
|
|
|
25 |
public:
|
|
|
26 |
const_iterator() { }
|
|
|
27 |
const_iterator(value_type *ptr) { m_ptr=ptr; }
|
|
|
28 |
const_iterator(const const_iterator& other) { m_ptr=other.m_ptr; }
|
|
|
29 |
|
|
|
30 |
const_iterator& operator ++() { m_ptr++; return *this; }
|
|
|
31 |
const_iterator operator ++(int) { m_ptr++; return const_iterator(m_ptr - 1); }
|
|
|
32 |
|
|
|
33 |
const_iterator& operator --() { m_ptr--; return *this; }
|
|
|
34 |
const_iterator operator --(int) { m_ptr--; return const_iterator(m_ptr + 1); }
|
|
|
35 |
|
|
|
36 |
const_reference operator * () const { return *m_ptr; }
|
|
|
37 |
const_reference operator -> () const { return *m_ptr; }
|
|
|
38 |
|
|
|
39 |
bool operator ==(const_iterator& right) const { return right.m_ptr==m_ptr; }
|
|
|
40 |
bool operator !=(const_iterator& right) const { return right.m_ptr!=m_ptr; }
|
|
|
41 |
};
|
|
|
42 |
|
|
|
43 |
class iterator : public const_iterator
|
|
|
44 |
{
|
|
|
45 |
public:
|
|
|
46 |
iterator() { }
|
|
|
47 |
iterator(value_type *ptr) : const_iterator(ptr) { }
|
|
|
48 |
iterator(const iterator& other) : const_iterator(other) { }
|
|
|
49 |
|
|
|
50 |
iterator& operator ++() { m_ptr++; return *this; }
|
|
|
51 |
iterator operator ++(int) { m_ptr++; return iterator(m_ptr - 1); }
|
|
|
52 |
|
|
|
53 |
iterator& operator --() { m_ptr--; return *this; }
|
|
|
54 |
iterator operator --(int) { m_ptr--; return iterator(m_ptr + 1); }
|
|
|
55 |
|
|
|
56 |
reference operator * () { return *m_ptr; }
|
|
|
57 |
reference operator -> () { return *m_ptr; }
|
|
|
58 |
};
|
|
|
59 |
|
|
|
60 |
protected:
|
|
|
61 |
value_type *m_first, *m_last, *m_end;
|
|
|
62 |
|
|
|
63 |
private:
|
|
|
64 |
size_type m_growby;
|
|
|
65 |
|
|
|
66 |
public:
|
|
|
67 |
size_type size() const { return m_last - m_first; }
|
|
|
68 |
size_type capacity() const { return m_end - m_first; }
|
|
|
69 |
|
|
|
70 |
size_type growby() const { return m_growby; }
|
|
|
71 |
void growby(size_type grow) const { m_growby=grow; }
|
|
|
72 |
|
|
|
73 |
array() { m_growby=100; m_first=0; clear(); }
|
|
|
74 |
array(size_type size) { m_growby=100; m_first=0; clear(); resize(size); }
|
|
|
75 |
~array() { delete[] m_first; }
|
|
|
76 |
|
|
|
77 |
void reserve(size_type newsize)
|
|
|
78 |
{
|
|
|
79 |
if(newsize > capacity()){
|
|
|
80 |
size_t oldsize=size();
|
|
|
81 |
value_type *newbuf=new value_type[newsize];
|
|
|
82 |
memcpy(newbuf, m_first, oldsize * sizeof(value_type));
|
|
|
83 |
delete[] m_first;
|
|
|
84 |
m_first=newbuf;
|
|
|
85 |
m_end=m_first + newsize;
|
|
|
86 |
m_last=m_first + oldsize;
|
|
|
87 |
}
|
|
|
88 |
}
|
|
|
89 |
|
|
|
90 |
void resize(size_type newsize)
|
|
|
91 |
{
|
|
|
92 |
if(newsize==0) return;
|
|
|
93 |
reserve(newsize);
|
|
|
94 |
m_last=m_first + newsize;
|
|
|
95 |
}
|
|
|
96 |
|
|
|
97 |
void resize(size_type newsize, value_type value)
|
|
|
98 |
{
|
|
|
99 |
resize(newsize);
|
|
|
100 |
value_type_ptr pos=m_first;
|
|
|
101 |
for(value_type_ptr pos=m_first; pos < m_last; pos++){
|
|
|
102 |
*pos=value;
|
|
|
103 |
}
|
|
|
104 |
}
|
|
|
105 |
|
|
|
106 |
void clear()
|
|
|
107 |
{
|
|
|
108 |
delete m_first;
|
|
|
109 |
m_first=0; m_last=0; m_end=0;
|
|
|
110 |
}
|
|
|
111 |
|
|
|
112 |
reference operator[](difference_type offset) { return *(m_first + offset); }
|
|
|
113 |
const_reference operator[](difference_type offset) const { return *(m_first + offset); }
|
|
|
114 |
|
|
|
115 |
reference at(difference_type offset) { return *(m_first + offset); }
|
|
|
116 |
const_reference at(difference_type offset) const { return *(m_first + offset); }
|
|
|
117 |
|
|
|
118 |
iterator begin() { return iterator(m_first); }
|
|
|
119 |
iterator end() { return iterator(m_last); }
|
|
|
120 |
|
|
|
121 |
const_iterator begin() const { return const_iterator(m_first); }
|
|
|
122 |
const_iterator end() const { return const_iterator(m_last); }
|
|
|
123 |
|
|
|
124 |
reference front() { return *begin(); }
|
|
|
125 |
reference back() { return *(--end()); }
|
|
|
126 |
|
|
|
127 |
const_reference front() const { return *begin(); }
|
|
|
128 |
const_reference back() const { return *(end() - 1); }
|
|
|
129 |
|
|
|
130 |
iterator push_back(const_reference val)
|
|
|
131 |
{
|
|
|
132 |
if(size() == capacity())
|
|
|
133 |
reserve(capacity() + growby());
|
|
|
134 |
*m_last=val;
|
|
|
135 |
return iterator(m_last++);
|
|
|
136 |
}
|
|
|
137 |
|
|
|
138 |
typedef int compare_callback (const void *, const void *);
|
|
|
139 |
|
|
|
140 |
void sort(compare_callback *callback)
|
|
|
141 |
{
|
|
|
142 |
qsort(m_first, size(), sizeof(value_type), callback);
|
|
|
143 |
}
|
|
|
144 |
|
|
|
145 |
void append(array<value_type>& other)
|
|
|
146 |
{
|
|
|
147 |
reserve(size() + other.size());
|
|
|
148 |
memcpy(m_first + size(), other.m_first, other.size() * sizeof(value_type));
|
|
|
149 |
m_last+=other.size();
|
|
|
150 |
}
|
|
|
151 |
|
|
|
152 |
};
|
|
|
153 |
|
|
|
154 |
}; // namespace ext
|
|
|
155 |
|
|
|
156 |
#endif // !defined(EXT_ARRAY_INCLUDED)
|