在创建StaticArray时,数组的大小必须是明确指定的,我们需要创建一个新的数组类,数组的大小可以动态的指定。
课程目标:
实验:
新建文件DynamicArray.h文件,如下:
1 #ifndef DYNAMICARRAY_H 2 #define DYNAMICARRAY_H 3 4 #include "Array.h" 5 #include "Exception.h" 6 7 namespace DTLib 8 { 9 10 template < typename T > 11 class DynamicArray : public Array<T> 12 { 13 protected: 14 int m_length; 15 public: 16 DynamicArray(int length) 17 { 18 this->m_array = new T[length]; 19 20 if(this->m_array != NULL) 21 { 22 this->m_length = length; 23 } 24 else 25 { 26 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to create DynamicArray Object..."); 27 } 28 } 29 30 DynamicArray(const DynamicArray<T>& obj) 31 { 32 this->m_array = new T[obj.m_length]; 33 34 if(this->m_array != NULL) 35 { 36 this->m_length = obj.m_length; 37 38 for(int i=0; i<obj.m_length; i++) 39 { 40 this->m_array[i] = obj.m_array[i]; 41 } 42 } 43 else 44 { 45 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to create DynamicArray Object..."); 46 } 47 } 48 49 DynamicArray<T>& operator= (const DynamicArray<T>& obj) 50 { 51 if( this != &obj ) 52 { 53 T* array = new T[obj.m_length]; 54 55 if( array != NULL ) 56 { 57 for(int i=0; i<obj.m_length; i++) 58 { 59 array[i] = obj.m_array[i]; 60 } 61 62 T* temp = this->m_array; 63 64 this->m_array = array; 65 this->m_length = obj.length; 66 67 delete[] temp; //先保存原来的指针,赋值新指针成功再释放原来的,保证异常安全 68 } 69 else 70 { 71 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to copy Object..."); 72 } 73 } 74 } 75 76 int length() const 77 { 78 return m_length; 79 } 80 81 void resize(int length) //动态重置数组的长度 82 { 83 if( length != m_length) 84 { 85 T* array = new T[length]; 86 87 if( array != NULL ) 88 { 89 int size = (length < m_length) ? length : m_length; 90 91 for(int i=0; i<size; i++) 92 { 93 array[i] = this->m_array[i]; 94 } 95 96 T* temp = this->m_array; 97 98 this->m_array = array; 99 this->m_length = length; 100 101 delete[] temp; 102 } 103 else 104 { 105 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to resize Object..."); 106 } 107 } 108 } 109 110 ~DynamicArray() 111 { 112 delete[] this->m_array; 113 } 114 }; 115 116 } 117 118 #endif // DYNAMICARRAY_H
测试程序如下:
#include <iostream> #include "DynamicArray.h" using namespace std; using namespace DTLib; int main() { DynamicArray<int> s1(5); for(int i = 0; i<s1.length(); i++) { s1[i] = i * i; } for(int i = 0; i < s1.length(); i++) { cout << s1[i] << endl; } return 0; }
结果如下:
第二个测试程序:
1 #include <iostream> 2 #include "DynamicArray.h" 3 4 5 using namespace std; 6 using namespace DTLib; 7 8 9 int main() 10 { 11 12 DynamicArray<int> s1(5); 13 14 for(int i = 0; i<s1.length(); i++) 15 { 16 s1[i] = i * i; 17 } 18 19 for(int i = 0; i < s1.length(); i++) 20 { 21 cout << s1[i] << endl; 22 } 23 24 DynamicArray<int> s2(10); 25 26 s2 = s1; 27 28 for(int i = 0; i < s2.length(); i++) 29 { 30 cout << s2[i] << endl; 31 } 32 33 34 35 return 0; 36 }
结果如下:
可以看到赋值之后,s2就只有5个元素了。
第三个测试程序:
1 #include <iostream> 2 #include "DynamicArray.h" 3 4 5 using namespace std; 6 using namespace DTLib; 7 8 9 int main() 10 { 11 12 DynamicArray<int> s1(5); 13 14 for(int i = 0; i<s1.length(); i++) 15 { 16 s1[i] = i * i; 17 } 18 19 for(int i = 0; i < s1.length(); i++) 20 { 21 cout << s1[i] << endl; 22 } 23 24 DynamicArray<int> s2(10); 25 26 s2 = s1; 27 28 s2.resize(3); 29 30 for(int i = 0; i < s2.length(); i++) 31 { 32 cout << s2[i] << endl; 33 } 34 35 s2[4] = 5; 36 37 38 return 0; 39 }
结果如下:
问题:
重构后的DynamicArray.h如下:
1 #ifndef DYNAMICARRAY_H 2 #define DYNAMICARRAY_H 3 4 #include "Array.h" 5 #include "Exception.h" 6 7 namespace DTLib 8 { 9 10 template < typename T > 11 class DynamicArray : public Array<T> 12 { 13 protected: 14 int m_length; 15 16 T* copy(T* array, int len, int newLen) 17 { 18 T* ret = new T[newLen]; 19 20 if( ret != NULL ) 21 { 22 int size = (len < newLen) ? len : newLen; 23 24 for(int i=0; i<size; i++) 25 { 26 ret[i] = array[i]; 27 } 28 } 29 30 return ret; 31 } 32 33 void update(T* array, int length) 34 { 35 if( array != NULL ) 36 { 37 T* temp = this->m_array; 38 39 this->m_array = array; 40 this->m_length = length; 41 42 delete[] temp; 43 } 44 else 45 { 46 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to update DynamicArray Object..."); 47 } 48 } 49 50 void init(T* array, int length) 51 { 52 if( array != NULL ) 53 { 54 this->m_array = array; 55 this->m_length = length; 56 } 57 else 58 { 59 THROW_EXCEPTION(NoEnoughMemoryException, "No memory to create DynamicArray Object..."); 60 } 61 } 62 63 public: 64 DynamicArray(int length) 65 { 66 init(new T[length], length); 67 } 68 69 DynamicArray(const DynamicArray<T>& obj) 70 { 71 init(copy(obj.m_array, obj.m_length, obj.m_length), obj.m_length); 72 } 73 74 DynamicArray<T>& operator= (const DynamicArray<T>& obj) 75 { 76 if( this != &obj ) 77 { 78 update(copy(obj.m_array, obj.m_length, obj.m_length), obj.m_length); 79 } 80 81 return *this; 82 } 83 84 int length() const 85 { 86 return m_length; 87 } 88 89 void resize(int length) //动态重置数组的长度 90 { 91 if( length != m_length) 92 { 93 update(copy(this->m_array, m_length, length), length); 94 } 95 } 96 97 ~DynamicArray() 98 { 99 delete[] this->m_array; 100 } 101 }; 102 103 } 104 105 #endif // DYNAMICARRAY_H
测试程序如下:
1 #include <iostream> 2 #include "DynamicArray.h" 3 4 5 using namespace std; 6 using namespace DTLib; 7 8 9 int main() 10 { 11 12 DynamicArray<int> s1(5); 13 14 for(int i = 0; i<s1.length(); i++) 15 { 16 s1[i] = i * i; 17 } 18 19 for(int i = 0; i < s1.length(); i++) 20 { 21 cout << s1[i] << endl; 22 } 23 24 DynamicArray<int> s2(10); 25 26 s2 = s1; 27 28 s2.resize(3); 29 30 for(int i = 0; i < s2.length(); i++) 31 { 32 cout << s2[i] << endl; 33 } 34 35 return 0; 36 }
结果如下:
小结: