C++实现动态数组功能

2020-01-06 19:44:41于丽

7.扩容

添加数据操作时需判断数组容量是否足够,若不够需考虑扩容。


template<class T>
void GenericArray<T>::renewCapacity()
{
 cout << "The array's capacity is small! Renew capacity.n";
 if (capacity < 1000)
 capacity = capacity << 1;
 else
 capacity = capacity >> 1 + capacity;
 if (!itemsFlag)
 {
 itemsFlag = 1;
 items = new T[capacity];
 for (int i = 0; i<counts; i++)
  *(items + i) = *(preitems + i);
  //items[i]=proitems[i];
 //cout << items << 'n';
 //cout << preitems << 'n';
 delete[]preitems;
 preitems = nullptr;
 }
 else
 {
 itemsFlag = 0;
 preitems = new T[capacity];
 for (int i = 0; i<counts; i++)
  *(preitems + i) = *(items + i);
 delete[]items;
 items = nullptr;
 }
}

8.添加数据:数组添加数据包括按索引下标插值、数组头插值、数组尾插值。实质上后两种都可以通过调用按索引下标插值函数实现。前文也提到过,数组添加操作中复杂的是大量的数据搬移工作:将某个元素按索引下标插入到数组第k个位置,需要将k ~ n部分的元素向后搬移一位,然后插入元素,更新元素数目。若插入到数组尾,时间复杂度O(1);插入到数组头,时间复杂度O(n);插入的平均时间复杂度为(1+2+…+n)/n = O(n)。
另外,还有一个优化问题:若数组是无序数组,则插入时不需要搬移数据:若将某个元素插入到数组第k个位置,首先将该位置的元素移动到数组末尾,然后将待插入元素插入到第k个位置,时间复杂度O(1)。


template<class T>
void GenericArray<T>::add(int index, T elem)
{
 if (isFull())
 {
 cout << "Array is full!" << 'n';
 renewCapacity();
 }
 if (checkIndex(index))
 if(!itemsFlag)
 {
  for (int i = counts; i > index; i--)
  preitems[i] = preitems[i - 1];
  preitems[index] = elem;
 }
 else
 {
  for (int i = counts; i > index; i--)
  items[i] = items[i - 1];
  items[index] = elem;
 }
 counts++;
 return;
}

template<class T>
void GenericArray<T>::addFirst(T elem)
{
 add(0, elem);
}

template<class T>
void GenericArray<T>::addLast(T elem)
{
 add(counts, elem);
}

9.删除数据:数组删除数据包括按索引下标删除、数组头删除、数组尾删除。实质上后两种都可以通过调用按索引下标删除函数实现。与前文类似,数组删除操作中复杂的也是大量的数据搬移工作:按索引下标将某个元素删除,需要将k+1 ~ n部分的元素向前搬移一位,更新元素数目。若删除数组尾,直接元素数目减一即可,时间复杂度O(1);删除数组头,时间复杂度O(n);删除的平均时间复杂度(1+2+…+n)/n = O(n)。