CCArray: performance improvements

CCArray:

- Iterator uses position for iterator. MUCH faster.
- Do not double init the array. performance improvements in memory.

Signed-off-by: Ricardo Quesada <ricardoquesada@gmail.com>
This commit is contained in:
Ricardo Quesada 2013-08-20 14:16:43 -07:00
parent 06b66e3427
commit 5225758c5c
2 changed files with 129 additions and 140 deletions

View File

@ -50,60 +50,60 @@ Array::Array(unsigned int capacity)
Array* Array::create() Array* Array::create()
{ {
Array* pArray = new Array(); Array* array = new Array();
if (pArray && pArray->init()) if (array && array->init())
{ {
pArray->autorelease(); array->autorelease();
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
return pArray; return array;
} }
Array* Array::createWithObject(Object* pObject) Array* Array::createWithObject(Object* object)
{ {
Array* pArray = new Array(); Array* array = new Array();
if (pArray && pArray->initWithObject(pObject)) if (array && array->initWithObject(object))
{ {
pArray->autorelease(); array->autorelease();
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
return pArray; return array;
} }
Array* Array::create(Object* pObject, ...) Array* Array::create(Object* object, ...)
{ {
va_list args; va_list args;
va_start(args,pObject); va_start(args,object);
Array* pArray = create(); Array* array = create();
if (pArray && pObject) if (array && object)
{ {
pArray->addObject(pObject); array->addObject(object);
Object *i = va_arg(args, Object*); Object *i = va_arg(args, Object*);
while(i) while(i)
{ {
pArray->addObject(i); array->addObject(i);
i = va_arg(args, Object*); i = va_arg(args, Object*);
} }
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
va_end(args); va_end(args);
return pArray; return array;
} }
Array* Array::createWithArray(Array* otherArray) Array* Array::createWithArray(Array* otherArray)
@ -113,23 +113,23 @@ Array* Array::createWithArray(Array* otherArray)
Array* Array::createWithCapacity(unsigned int capacity) Array* Array::createWithCapacity(unsigned int capacity)
{ {
Array* pArray = new Array(); Array* array = new Array();
if (pArray && pArray->initWithCapacity(capacity)) if (array && array->initWithCapacity(capacity))
{ {
pArray->autorelease(); array->autorelease();
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
return pArray; return array;
} }
Array* Array::createWithContentsOfFile(const char* pFileName) Array* Array::createWithContentsOfFile(const char* fileName)
{ {
Array* pRet = Array::createWithContentsOfFileThreadSafe(pFileName); Array* pRet = Array::createWithContentsOfFileThreadSafe(fileName);
if (pRet != NULL) if (pRet != NULL)
{ {
pRet->autorelease(); pRet->autorelease();
@ -137,9 +137,9 @@ Array* Array::createWithContentsOfFile(const char* pFileName)
return pRet; return pRet;
} }
Array* Array::createWithContentsOfFileThreadSafe(const char* pFileName) Array* Array::createWithContentsOfFileThreadSafe(const char* fileName)
{ {
return FileUtils::getInstance()->createArrayWithContentsOfFile(pFileName); return FileUtils::getInstance()->createArrayWithContentsOfFile(fileName);
} }
bool Array::init() bool Array::init()
@ -147,43 +147,43 @@ bool Array::init()
return initWithCapacity(1); return initWithCapacity(1);
} }
bool Array::initWithObject(Object* pObject) bool Array::initWithObject(Object* object)
{ {
bool bRet = initWithCapacity(1); bool ret = initWithCapacity(1);
if (bRet) if (ret)
{ {
addObject(pObject); addObject(object);
} }
return bRet; return ret;
} }
/** Initializes an array with some objects */ /** Initializes an array with some objects */
bool Array::initWithObjects(Object* pObject, ...) bool Array::initWithObjects(Object* object, ...)
{ {
bool bRet = false; bool ret = false;
do do
{ {
CC_BREAK_IF(pObject == NULL); CC_BREAK_IF(object == NULL);
va_list args; va_list args;
va_start(args, pObject); va_start(args, object);
if (pObject) if (object)
{ {
this->addObject(pObject); this->addObject(object);
Object* i = va_arg(args, Object*); Object* i = va_arg(args, Object*);
while(i) while(i)
{ {
this->addObject(i); this->addObject(i);
i = va_arg(args, Object*); i = va_arg(args, Object*);
} }
bRet = true; ret = true;
} }
va_end(args); va_end(args);
} while (false); } while (false);
return bRet; return ret;
} }
bool Array::initWithCapacity(unsigned int capacity) bool Array::initWithCapacity(unsigned int capacity)
@ -274,13 +274,13 @@ void Array::setObject(Object* object, int index)
data[index] = RCPtr<Object>(object); data[index] = RCPtr<Object>(object);
} }
void Array::removeLastObject(bool bReleaseObj) void Array::removeLastObject(bool releaseObj)
{ {
CCASSERT(data.size(), "no objects added"); CCASSERT(data.size(), "no objects added");
data.pop_back(); data.pop_back();
} }
void Array::removeObject(Object* object, bool bReleaseObj /* ignored */) void Array::removeObject(Object* object, bool releaseObj /* ignored */)
{ {
// auto begin = data.begin(); // auto begin = data.begin();
// auto end = data.end(); // auto end = data.end();
@ -301,7 +301,7 @@ void Array::removeObject(Object* object, bool bReleaseObj /* ignored */)
} }
} }
void Array::removeObjectAtIndex(unsigned int index, bool bReleaseObj /* ignored */) void Array::removeObjectAtIndex(unsigned int index, bool releaseObj /* ignored */)
{ {
auto obj = data[index]; auto obj = data[index];
data.erase( data.begin() + index ); data.erase( data.begin() + index );
@ -342,10 +342,10 @@ void Array::exchangeObjectAtIndex(unsigned int index1, unsigned int index2)
std::swap( data[index1], data[index2] ); std::swap( data[index1], data[index2] );
} }
void Array::replaceObjectAtIndex(unsigned int index, Object* pObject, bool bReleaseObject /* ignored */) void Array::replaceObjectAtIndex(unsigned int index, Object* object, bool releaseObject /* ignored */)
{ {
// auto obj = data[index]; // auto obj = data[index];
data[index] = pObject; data[index] = object;
} }
void Array::reverseObjects() void Array::reverseObjects()
@ -404,7 +404,7 @@ void Array::acceptVisitor(DataVisitor &visitor)
Array::Array() Array::Array()
: data(NULL) : data(NULL)
{ {
init(); // init();
} }
Array::Array(unsigned int capacity) Array::Array(unsigned int capacity)
@ -415,60 +415,60 @@ Array::Array(unsigned int capacity)
Array* Array::create() Array* Array::create()
{ {
Array* pArray = new Array(); Array* array = new Array();
if (pArray && pArray->init()) if (array && array->init())
{ {
pArray->autorelease(); array->autorelease();
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
return pArray; return array;
} }
Array* Array::createWithObject(Object* pObject) Array* Array::createWithObject(Object* object)
{ {
Array* pArray = new Array(); Array* array = new Array();
if (pArray && pArray->initWithObject(pObject)) if (array && array->initWithObject(object))
{ {
pArray->autorelease(); array->autorelease();
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
return pArray; return array;
} }
Array* Array::create(Object* pObject, ...) Array* Array::create(Object* object, ...)
{ {
va_list args; va_list args;
va_start(args,pObject); va_start(args,object);
Array* pArray = create(); Array* array = create();
if (pArray && pObject) if (array && object)
{ {
pArray->addObject(pObject); array->addObject(object);
Object *i = va_arg(args, Object*); Object *i = va_arg(args, Object*);
while(i) while(i)
{ {
pArray->addObject(i); array->addObject(i);
i = va_arg(args, Object*); i = va_arg(args, Object*);
} }
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
va_end(args); va_end(args);
return pArray; return array;
} }
Array* Array::createWithArray(Array* otherArray) Array* Array::createWithArray(Array* otherArray)
@ -478,23 +478,23 @@ Array* Array::createWithArray(Array* otherArray)
Array* Array::createWithCapacity(unsigned int capacity) Array* Array::createWithCapacity(unsigned int capacity)
{ {
Array* pArray = new Array(); Array* array = new Array();
if (pArray && pArray->initWithCapacity(capacity)) if (array && array->initWithCapacity(capacity))
{ {
pArray->autorelease(); array->autorelease();
} }
else else
{ {
CC_SAFE_DELETE(pArray); CC_SAFE_DELETE(array);
} }
return pArray; return array;
} }
Array* Array::createWithContentsOfFile(const char* pFileName) Array* Array::createWithContentsOfFile(const char* fileName)
{ {
Array* pRet = Array::createWithContentsOfFileThreadSafe(pFileName); Array* pRet = Array::createWithContentsOfFileThreadSafe(fileName);
if (pRet != NULL) if (pRet != NULL)
{ {
pRet->autorelease(); pRet->autorelease();
@ -502,9 +502,9 @@ Array* Array::createWithContentsOfFile(const char* pFileName)
return pRet; return pRet;
} }
Array* Array::createWithContentsOfFileThreadSafe(const char* pFileName) Array* Array::createWithContentsOfFileThreadSafe(const char* fileName)
{ {
return FileUtils::getInstance()->createArrayWithContentsOfFile(pFileName); return FileUtils::getInstance()->createArrayWithContentsOfFile(fileName);
} }
bool Array::init() bool Array::init()
@ -512,67 +512,71 @@ bool Array::init()
return initWithCapacity(1); return initWithCapacity(1);
} }
bool Array::initWithObject(Object* pObject) bool Array::initWithObject(Object* object)
{ {
ccArrayFree(data); CCASSERT(!data, "Array cannot be re-initialized");
bool bRet = initWithCapacity(1);
if (bRet) bool ret = initWithCapacity(1);
if (ret)
{ {
addObject(pObject); addObject(object);
} }
return bRet; return ret;
} }
/** Initializes an array with some objects */ /** Initializes an array with some objects */
bool Array::initWithObjects(Object* pObject, ...) bool Array::initWithObjects(Object* object, ...)
{ {
ccArrayFree(data); CCASSERT(!data, "Array cannot be re-initialized");
bool bRet = false;
bool ret = false;
do do
{ {
CC_BREAK_IF(pObject == NULL); CC_BREAK_IF(object == NULL);
va_list args; va_list args;
va_start(args, pObject); va_start(args, object);
if (pObject) if (object)
{ {
this->addObject(pObject); this->addObject(object);
Object* i = va_arg(args, Object*); Object* i = va_arg(args, Object*);
while(i) while(i)
{ {
this->addObject(i); this->addObject(i);
i = va_arg(args, Object*); i = va_arg(args, Object*);
} }
bRet = true; ret = true;
} }
va_end(args); va_end(args);
} while (false); } while (false);
return bRet; return ret;
} }
bool Array::initWithCapacity(unsigned int capacity) bool Array::initWithCapacity(unsigned int capacity)
{ {
ccArrayFree(data); CCASSERT(!data, "Array cannot be re-initialized");
data = ccArrayNew(capacity); data = ccArrayNew(capacity);
return true; return true;
} }
bool Array::initWithArray(Array* otherArray) bool Array::initWithArray(Array* otherArray)
{ {
ccArrayFree(data); CCASSERT(!data, "Array cannot be re-initialized");
bool bRet = false;
bool ret = false;
do do
{ {
CC_BREAK_IF(! initWithCapacity(otherArray->data->num)); CC_BREAK_IF(! initWithCapacity(otherArray->data->num));
addObjectsFromArray(otherArray); addObjectsFromArray(otherArray);
bRet = true; ret = true;
} while (0); } while (0);
return bRet; return ret;
} }
int Array::getIndexOfObject(Object* object) const int Array::getIndexOfObject(Object* object) const
@ -640,20 +644,20 @@ void Array::setObject(Object* object, int index)
} }
} }
void Array::removeLastObject(bool bReleaseObj) void Array::removeLastObject(bool releaseObj)
{ {
CCASSERT(data->num, "no objects added"); CCASSERT(data->num, "no objects added");
ccArrayRemoveObjectAtIndex(data, data->num-1, bReleaseObj); ccArrayRemoveObjectAtIndex(data, data->num-1, releaseObj);
} }
void Array::removeObject(Object* object, bool bReleaseObj/* = true*/) void Array::removeObject(Object* object, bool releaseObj/* = true*/)
{ {
ccArrayRemoveObject(data, object, bReleaseObj); ccArrayRemoveObject(data, object, releaseObj);
} }
void Array::removeObjectAtIndex(unsigned int index, bool bReleaseObj) void Array::removeObjectAtIndex(unsigned int index, bool releaseObj)
{ {
ccArrayRemoveObjectAtIndex(data, index, bReleaseObj); ccArrayRemoveObjectAtIndex(data, index, releaseObj);
} }
void Array::removeObjectsInArray(Array* otherArray) void Array::removeObjectsInArray(Array* otherArray)
@ -698,9 +702,9 @@ void Array::exchangeObjectAtIndex(unsigned int index1, unsigned int index2)
ccArraySwapObjectsAtIndexes(data, index1, index2); ccArraySwapObjectsAtIndexes(data, index1, index2);
} }
void Array::replaceObjectAtIndex(unsigned int index, Object* pObject, bool bReleaseObject/* = true*/) void Array::replaceObjectAtIndex(unsigned int index, Object* object, bool releaseObject/* = true*/)
{ {
ccArrayInsertObjectAtIndex(data, pObject, index); ccArrayInsertObjectAtIndex(data, object, index);
ccArrayRemoveObjectAtIndex(data, index+1); ccArrayRemoveObjectAtIndex(data, index+1);
} }
@ -765,26 +769,12 @@ void Array::acceptVisitor(DataVisitor &visitor)
Array::iterator Array::begin() Array::iterator Array::begin()
{ {
if (count() > 0) return Array::ArrayIterator(0, this);
{
return Array::ArrayIterator( getObjectAtIndex(0), this);
}
else
{
return Array::ArrayIterator(nullptr, nullptr);;
}
} }
Array::iterator Array::end() Array::iterator Array::end()
{ {
if (count() > 0) return Array::ArrayIterator(count(), this);
{
return Array::ArrayIterator(getObjectAtIndex(count()), this);
}
else
{
return Array::ArrayIterator(nullptr, nullptr);
}
} }
#endif // uses ccArray #endif // uses ccArray

View File

@ -210,7 +210,7 @@ do { \
} \ } \
while(false) while(false)
#define arrayMakeObjectsPerformSelectorWithObject(pArray, func, pObject, elementType) \ #define arrayMakeObjectsPerformSelectorWithObject(pArray, func, object, elementType) \
do { \ do { \
if(pArray && pArray->count() > 0) \ if(pArray && pArray->count() > 0) \
{ \ { \
@ -220,7 +220,7 @@ do { \
elementType pNode = static_cast<elementType>(child); \ elementType pNode = static_cast<elementType>(child); \
if(pNode) \ if(pNode) \
{ \ { \
pNode->func(pObject); \ pNode->func(object); \
} \ } \
} \ } \
} \ } \
@ -237,9 +237,9 @@ public:
/** Create an array */ /** Create an array */
static Array* create(); static Array* create();
/** Create an array with some objects */ /** Create an array with some objects */
static Array* create(Object* pObject, ...) CC_REQUIRES_NULL_TERMINATION; static Array* create(Object* object, ...) CC_REQUIRES_NULL_TERMINATION;
/** Create an array with one object */ /** Create an array with one object */
static Array* createWithObject(Object* pObject); static Array* createWithObject(Object* object);
/** Create an array with capacity */ /** Create an array with capacity */
static Array* createWithCapacity(unsigned int capacity); static Array* createWithCapacity(unsigned int capacity);
/** Create an array with an existing array */ /** Create an array with an existing array */
@ -262,9 +262,9 @@ public:
/** Initializes an array */ /** Initializes an array */
bool init(); bool init();
/** Initializes an array with one object */ /** Initializes an array with one object */
bool initWithObject(Object* pObject); bool initWithObject(Object* object);
/** Initializes an array with some objects */ /** Initializes an array with some objects */
bool initWithObjects(Object* pObject, ...) CC_REQUIRES_NULL_TERMINATION; bool initWithObjects(Object* object, ...) CC_REQUIRES_NULL_TERMINATION;
/** Initializes an array with capacity */ /** Initializes an array with capacity */
bool initWithCapacity(unsigned int capacity); bool initWithCapacity(unsigned int capacity);
/** Initializes an array with an existing array */ /** Initializes an array with an existing array */
@ -319,7 +319,7 @@ public:
/** Returns a Boolean value that indicates whether object is present in array. */ /** Returns a Boolean value that indicates whether object is present in array. */
bool containsObject(Object* object) const; bool containsObject(Object* object) const;
/** @since 1.1 */ /** @since 1.1 */
bool isEqualToArray(Array* pOtherArray); bool isEqualToArray(Array* otherArray);
// Adding Objects // Adding Objects
/** Add a certain object */ /** Add a certain object */
@ -352,11 +352,11 @@ public:
// Removing Objects // Removing Objects
/** Remove last object */ /** Remove last object */
void removeLastObject(bool bReleaseObj = true); void removeLastObject(bool releaseObj = true);
/** Remove a certain object */ /** Remove a certain object */
void removeObject(Object* object, bool bReleaseObj = true); void removeObject(Object* object, bool releaseObj = true);
/** Remove an element with a certain index */ /** Remove an element with a certain index */
void removeObjectAtIndex(unsigned int index, bool bReleaseObj = true); void removeObjectAtIndex(unsigned int index, bool releaseObj = true);
/** Remove all elements */ /** Remove all elements */
void removeObjectsInArray(Array* otherArray); void removeObjectsInArray(Array* otherArray);
/** Remove all objects */ /** Remove all objects */
@ -374,7 +374,7 @@ public:
void exchangeObjectAtIndex(unsigned int index1, unsigned int index2); void exchangeObjectAtIndex(unsigned int index1, unsigned int index2);
/** Replace object at index with another object. */ /** Replace object at index with another object. */
void replaceObjectAtIndex(unsigned int uIndex, Object* pObject, bool bReleaseObject = true); void replaceObjectAtIndex(unsigned int index, Object* object, bool releaseObject = true);
/** Revers the array */ /** Revers the array */
void reverseObjects(); void reverseObjects();
@ -401,28 +401,27 @@ public:
class ArrayIterator : public std::iterator<std::input_iterator_tag, Object> class ArrayIterator : public std::iterator<std::input_iterator_tag, Object>
{ {
public: public:
ArrayIterator(Object *object, Array *array) : _ptr(object), _parent(array) {} ArrayIterator(int index, Array *array) : _index(index), _parent(array) {}
ArrayIterator(const ArrayIterator& arrayIterator) : _ptr(arrayIterator._ptr), _parent(arrayIterator._parent) {} ArrayIterator(const ArrayIterator& arrayIterator) : _index(arrayIterator._index), _parent(arrayIterator._parent) {}
ArrayIterator& operator++() ArrayIterator& operator++()
{ {
int index = _parent->getIndexOfObject(_ptr); ++_index;
_ptr = _parent->getObjectAtIndex(index+1);
return *this; return *this;
} }
ArrayIterator operator++(int) ArrayIterator operator++(int dummy)
{ {
ArrayIterator tmp(*this); ArrayIterator tmp(*this);
(*this)++; (*this)++;
return tmp; return tmp;
} }
bool operator==(const ArrayIterator& rhs) { return _ptr == rhs._ptr; } bool operator==(const ArrayIterator& rhs) { return _index == rhs._index; }
bool operator!=(const ArrayIterator& rhs) { return _ptr != rhs._ptr; } bool operator!=(const ArrayIterator& rhs) { return _index != rhs._index; }
Object* operator*() { return _ptr; } Object* operator*() { return _parent->getObjectAtIndex(_index); }
Object* operator->() { return _ptr; } Object* operator->() { return _parent->getObjectAtIndex(_index); }
private: private:
Object *_ptr; int _index;
Array *_parent; Array *_parent;
}; };