* Made the semantics of _Resize() more consequent. Even, if the capacity
doesn't change, it makes room for/removes items at the given index. This simplifies the calling methods. * Added InsertUninitialized() method, a generalized version of AddUninitialized(). * Remove(): - Added optional "count" parameter. - Added missing debugger() call. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@34566 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -5,10 +5,13 @@
|
|||||||
#ifndef ARRAY_H
|
#ifndef ARRAY_H
|
||||||
#define ARRAY_H
|
#define ARRAY_H
|
||||||
|
|
||||||
|
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <string.h>
|
#include <string.h>
|
||||||
|
|
||||||
|
#include <OS.h>
|
||||||
|
|
||||||
|
|
||||||
template<typename Element>
|
template<typename Element>
|
||||||
class Array {
|
class Array {
|
||||||
@@ -25,7 +28,8 @@ public:
|
|||||||
inline bool Add(const Element& element);
|
inline bool Add(const Element& element);
|
||||||
inline bool AddUninitialized(int elementCount);
|
inline bool AddUninitialized(int elementCount);
|
||||||
inline bool Insert(const Element& element, int index);
|
inline bool Insert(const Element& element, int index);
|
||||||
inline bool Remove(int index);
|
inline bool InsertUninitialized(int index, int count);
|
||||||
|
inline bool Remove(int index, int count = 1);
|
||||||
|
|
||||||
void Clear();
|
void Clear();
|
||||||
inline void MakeEmpty();
|
inline void MakeEmpty();
|
||||||
@@ -82,10 +86,8 @@ template<typename Element>
|
|||||||
bool
|
bool
|
||||||
Array<Element>::Add(const Element& element)
|
Array<Element>::Add(const Element& element)
|
||||||
{
|
{
|
||||||
if (fSize == fCapacity) {
|
if (!_Resize(fSize, 1))
|
||||||
if (!_Resize(fSize, 1))
|
return false;
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
fElements[fSize] = element;
|
fElements[fSize] = element;
|
||||||
fSize++;
|
fSize++;
|
||||||
@@ -94,19 +96,10 @@ Array<Element>::Add(const Element& element)
|
|||||||
|
|
||||||
|
|
||||||
template<typename Element>
|
template<typename Element>
|
||||||
bool
|
inline bool
|
||||||
Array<Element>::AddUninitialized(int elementCount)
|
Array<Element>::AddUninitialized(int elementCount)
|
||||||
{
|
{
|
||||||
if (elementCount < 0)
|
return InsertUninitialized(fSize, elementCount);
|
||||||
return false;
|
|
||||||
|
|
||||||
if (fSize + elementCount > fCapacity) {
|
|
||||||
if (!_Resize(fSize, elementCount))
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
fSize += elementCount;
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -117,13 +110,8 @@ Array<Element>::Insert(const Element& element, int index)
|
|||||||
if (index < 0 || index > fSize)
|
if (index < 0 || index > fSize)
|
||||||
index = fSize;
|
index = fSize;
|
||||||
|
|
||||||
if (fSize == fCapacity) {
|
if (!_Resize(index, 1))
|
||||||
if (!_Resize(index, 1))
|
return false;
|
||||||
return false;
|
|
||||||
} else if (index < fSize) {
|
|
||||||
memmove(fElements + index + 1, fElements + index,
|
|
||||||
sizeof(Element) * (fSize - index));
|
|
||||||
}
|
|
||||||
|
|
||||||
fElements[index] = element;
|
fElements[index] = element;
|
||||||
fSize++;
|
fSize++;
|
||||||
@@ -133,23 +121,45 @@ Array<Element>::Insert(const Element& element, int index)
|
|||||||
|
|
||||||
template<typename Element>
|
template<typename Element>
|
||||||
bool
|
bool
|
||||||
Array<Element>::Remove(int index)
|
Array<Element>::InsertUninitialized(int index, int count)
|
||||||
{
|
{
|
||||||
if (index < 0 || index >= fSize) {
|
if (index < 0 || index > fSize || count < 0)
|
||||||
|
return false;
|
||||||
|
if (count == 0)
|
||||||
|
return true;
|
||||||
|
|
||||||
|
if (!_Resize(index, count))
|
||||||
|
return false;
|
||||||
|
|
||||||
|
fSize += count;
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
template<typename Element>
|
||||||
|
bool
|
||||||
|
Array<Element>::Remove(int index, int count)
|
||||||
|
{
|
||||||
|
if (index < 0 || count < 0 || index + count > fSize) {
|
||||||
|
#if DEBUG
|
||||||
char buffer[128];
|
char buffer[128];
|
||||||
snprintf(buffer, sizeof(buffer), "Array::Remove(): index: %d, size: %d",
|
snprintf(buffer, sizeof(buffer), "Array::Remove(): index: %d, "
|
||||||
index, fSize);
|
"count: %d, size: %d", index, count, fSize);
|
||||||
|
debugger(buffer);
|
||||||
|
#endif
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
if (count == 0)
|
||||||
|
return true;
|
||||||
|
|
||||||
if (fSize <= fCapacity / 2 && fCapacity > kMinCapacity) {
|
if (index + count < fSize) {
|
||||||
_Resize(index, -1);
|
memmove(fElements + index, fElements + index + count,
|
||||||
} else if (index < fSize) {
|
sizeof(Element) * (fSize - index - count));
|
||||||
memmove(fElements + index, fElements + index + 1,
|
|
||||||
sizeof(Element) * (fSize - index - 1));
|
|
||||||
}
|
}
|
||||||
|
|
||||||
fSize--;
|
_Resize(index, -count);
|
||||||
|
|
||||||
|
fSize -= count;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -234,8 +244,22 @@ Array<Element>::_Resize(int index, int delta)
|
|||||||
while (newCapacity < newSize)
|
while (newCapacity < newSize)
|
||||||
newCapacity *= 2;
|
newCapacity *= 2;
|
||||||
|
|
||||||
if (newCapacity == fCapacity)
|
if (newCapacity == fCapacity) {
|
||||||
|
// the capacity doesn't change -- still make room for/remove elements
|
||||||
|
if (index < fSize) {
|
||||||
|
if (delta > 0) {
|
||||||
|
// leave a gap of delta elements
|
||||||
|
memmove(fElements + index + delta, fElements + index,
|
||||||
|
(fSize - index) * sizeof(Element));
|
||||||
|
} else if (index < fSize + delta) {
|
||||||
|
// drop -delta elements
|
||||||
|
memcpy(fElements + index, fElements + index - delta,
|
||||||
|
(fSize - index + delta) * sizeof(Element));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
// allocate new array
|
// allocate new array
|
||||||
Element* elements = (Element*)malloc(newCapacity * sizeof(Element));
|
Element* elements = (Element*)malloc(newCapacity * sizeof(Element));
|
||||||
|
|||||||
Reference in New Issue
Block a user