数据结构(04)_数组类的实现
C++中支持原生数组,但由于原生数组的天然缺陷(不能获取长度信息、越界访问不会报错...),我们有必要来开发自己的数组类,从而解决这些问题。
数组类的继承关系如图:
需求分析:
1、由于线性表,不能作为数组直接使用,我们需要自己实现一个数组类来代替原生数组。
2、解决原生数组越界访问不会报错的问题
3、提供数组的长度信息
template < typename T >class Array : public Object{protected:T *m_array;public:T& operator [] (int index)T operator [] (int index) constbool get(int index, const T& e)bool set(int index, const T& e)virtual int length(void) = 0;};
1.3. Array的实现
template < typename T >class Array : public Object{protected: T *m_array;public: T& operator [] (int index) { if( (index>=0) && (index<length()) ) { return m_array[index]; } else { THROW_EXCEPTION(IndexOutOfBoundsException, "array index out of range..."); } } T operator [] (int index) const { return const_cast<Array<T>&>(*this)[index]; } bool get(int index, const T& e) { bool ret = (index>=0) && (index<length()); if( ret ) { e = m_array[index]; } return ret; } bool set(int index, const T& e) { bool ret = (index>=0) && (index<length); if( ret ) { m_array[index] = e; } return ret; } virtual int length(void) = 0;};
1.4.StaticArray设计要点
设计要点:
封装原生数组;使用模板参数决定数组大小实现函数返回数组长度拷贝构造和赋值重载template < typename T, int N >class StaticArray : public Array<T> protected:T m_space[N];public:StaticArray()// 提供拷贝构造喊赋值重载函数,实现数组的拷贝StaticArray(const StaticArray<T, N>& obj)T& operator = (const StaticArray<T, N>& obj)int length(void)};
1.5. StaticArray的实现
template <typename T, int N>class StaticArray : public Array<T>{protected: T m_space[N];public: StaticArray() { this->m_array = m_space; } StaticArray(const StaticArray<T, N>& obj) { this->m_array = m_space; for(int i=0; i<length();i++) // 数组元素拷贝 { m_space[i] = obj.m_space[i]; } } T& operator ==(const StaticArray<T, N>& obj) { if(this != &obj) { this->m_array = m_space; for(int i=0; i<length();i++) { m_space[i] = obj.m_space[i]; } } } int length(void) { return N; }};
2.数组类的实现_22.1.DynamicArray设计要点
设计要点:类模板
动态确定内部数组空间的大小实现函数返回数组的长度拷贝构造和赋值操作template < typename T >class DynamicArray : public Array<T>{protected:int m_length;public:DynamicArray(int length)DynamicArray(const DynamicArray<T>& obj)DynamicArray<T>& operator = (const DynamicArray<T>& obj)void resize(int length)~DynamicArray()};
2.2.DynamicArray代码优化
DynamicArray类中的函数实现存在重复的逻辑,可以进行代码优化。
重复代码逻辑的抽象:
— init 函数中实现对象构造时的初始化操作
— copy 函数负责从堆空间中申请内存,并执行拷贝构造操作
— updata 将指定的堆空间作为内部存储数组使用
template <typename T>class DynamicList : public SeqList<T>{protected: int m_capacity;public: DynamicList(int capacity) { this->m_array = new T[capacity]; if(this->m_array != NULL) { this->m_length = 0; this->m_capacity = capacity; } else { THROW_EXCEPTION(NoEnoughMemoryException,"No memory to create DynamicList object ..."); } } int capacity()const { return m_capacity; } void resize(int capacity) { if(capacity != m_capacity) { T* array = new T[capacity]; if(array != NULL) { int length = (this->m_length < capacity ? this->m_length : capacity); for(int i=0;i<length;i++) { array[i] = this->m_array[i]; } T* temp = this->m_array; this->m_array = array; this->m_length = length; this->m_capacity = capacity; delete[] temp; } else { THROW_EXCEPTION(NoEnoughMemoryException,"No memory to create DynamicList object ..."); } } } ~DynamicList() { delete[] this->m_array; }};
总结:
StaticArray通过封装原生数组的方式,实现数组类DynamicArray动态申请堆空间,使得数组长度动态可变数组对象能够代替原生数组,并且使用上更安全代码优化时项目开发必不可少的环节声明:本站所有文章资源内容,如无特殊说明或标注,均为采集网络资源。如若本站内容侵犯了原著者的合法权益,可联系本站删除。