/* 案例描述:实现一个通用的数组类,要求如下:
* (1)可以对内置数据类型以及自定义数据类型的数据进行储存;
* (2)将数组中的数据储存到堆区;
* (3)构造函数中可以传入数组的容量;
* (4)提供对应的拷贝构造函数以及operator=赋值操作重载防止浅拷贝问题;
* (5)提供尾插法和尾删法对数组中的数据进行增加和删除;
* (6)可以通过下标的方式访问数组中的元素;
* (7)可以获取数组中当前元素个数和数组的容量。
*/
类模板声明及实现
其中,类的声明以及实现均放在一个文件udfArray.hpp中:
//
// Created by shexuan on 2021/1/17.
//
#pragma once
#include <iostream>
#include <string>
using namespace std;
template <class T>
class MyArray{
public:
// 构造函数(传入容量)
MyArray(int capacity);
// 拷贝构造
MyArray(const MyArray<T> & arr);
// operator= 重载, 防止浅拷贝, 引用方式返回,以便后续可以连续赋值 a=b=c
MyArray & operator=(const MyArray<T> &arr);
// 利用下标访问数组的元素
T& operator[](int index);
// 尾插法
void Push_Back(const T& val);
// 尾删法
void Del_Back();
// 获取数组容量
int get_Capacity();
// 获取数组当前存放元素数量
int get_Size();
// 析构函数
~MyArray();
private:
// 数组, 因为数组数据开辟到堆区存放,因此这里用指针
T *pAddress;
// 数组容量,也即能存放的元素最大数量
int m_Capacity;
// 当前存放的数组大小
int m_Size;
};
// 有参构造函数
template <class T>
MyArray<T>::MyArray(int capacity) {
cout << "有参构造函数" << endl;
this->m_Size = 0;
this->m_Capacity = capacity;
this->pAddress = new T[capacity];
}
// 拷贝构造函数
template <class T>
MyArray<T>::MyArray(const MyArray<T> &arr) {
cout << "拷贝构造函数" << endl;
this->m_Capacity = arr.m_Capacity;
this->m_Size = arr.m_Size;
// 深拷贝
this->pAddress = new T[arr.m_Capacity];
// 将arr中的元素拷贝过来
for(int i=0; i<arr.m_Size; i++){
this->pAddress[i] = arr.pAddress[i];
}
}
// 赋值运算符重载
template <class T>
MyArray<T>& MyArray<T>:: operator=(const MyArray<T> &arr){
cout << "运算符重载" << endl;
// 先判断原来堆区是否有数据,如果有则先释放
if(this->pAddress!=NULL){
delete [] this->pAddress;
this->pAddress = NULL;
this->m_Size = 0;
this->m_Capacity = 0;
}
// 深拷贝
this->m_Capacity = arr.m_Capacity;
this->m_Size = arr.m_Size;
this->pAddress = new T[this->m_Capacity];
for (int i=0; i<this->m_Size; i++){
this->pAddress[i] = arr.pAddress[i];
}
// 这一步一定要返回,不然相当于赋值拷贝生成一个匿名MyArray实例,马上就又被删除了,无法赋值
return *this;
};
// 尾插法
template <class T>
void MyArray<T>::Push_Back(const T& val){
// 先判断数组容量是否已满
if (this->m_Size==this->m_Capacity){
cout << "数组已满,无法插入数据" << endl;
}else{
this->pAddress[m_Size] = val;
this->m_Size ++;
}
};
// 尾删法
template <class T>
void MyArray<T>::Del_Back() {
// 先判断,如果数组为空,则不进行操作
if(this->m_Size==0){
cout << "当前数组为空!" << endl;
}else{
this->m_Size--;
}
}
// 利用下标访问数组的元素, 返回引用使得可以下标赋值:arr[0]=100;
template <class T>
T& MyArray<T>::operator[](int index) {
// 这里其实应该加个catch防止out of index
return this->pAddress[index];
}
// 获取数组容量
template <class T>
int MyArray<T>::get_Capacity(){
return this->m_Capacity;
}
// 获取数组当前存放元素数量
template <class T>
int MyArray<T>::get_Size(){
return this->m_Size;
}
// 析构函数, 手动释放存在堆区的数据
template <class T>
MyArray<T>::~MyArray(){
cout << "析构函数" << endl;
if (this->pAddress!=NULL){
delete [] this->pAddress;
this->pAddress = NULL;
}
}
测试
//
// Created by shexuan on 2021/1/17.
//
#include <iostream>
#include <string>
using namespace std;
#include "udfArray.hpp"
/* 案例描述:实现一个通用的数组类,要求如下:
* (1)可以对内置数据类型以及自定义数据类型的数据进行储存;
* (2)将数组中的数据储存到堆区;
* (3)构造函数中可以传入数组的容量;
* (4)提供对应的拷贝构造函数以及operator=赋值操作重载防止浅拷贝问题;
* (5)提供尾插法和尾删法对数组中的数据进行增加和删除;
* (6)可以通过下标的方式访问数组中的元素;
* (7)可以获取数组中当前元素个数和数组的容量。
*
*/
class Person{
public:
Person(){}; // 默认构造函数
Person(string name, int age){
this->m_name = name;
this->m_age = age;
};
int m_age;
string m_name;
};
template <class T>
void printArr(const MyArray<T> &arr, int len){
for (int i=0; i<len; i++){
cout << i << " ";
}
cout << endl;
}
void printUdfArr(MyArray<Person> &arr){
for (int i=0; i<arr.get_Size(); i++){
cout << "\t姓名:" << arr[i].m_name << "\t年龄:"<<arr[i].m_age << endl;
}
}
void test01(){
MyArray<int> arr1(10);
for (int i=0;i<10;i++){
arr1.Push_Back(i);
}
int len = arr1.get_Size();
cout << len << endl;
printArr<int> (arr1, len);
cout << "尾删前:" << endl;
cout << "arr1的容量为:" << arr1.get_Capacity() << endl;
cout << "arr1的元素数量为:" << arr1.get_Size() << endl;
// MyArray<int> arr2(arr1);
// MyArray<int> arr3(100);
// arr3 = arr1;
arr1.Del_Back();
cout << "尾删后:" << endl;
cout << "arr1的容量为:" << arr1.get_Capacity() << endl;
cout << "arr1的元素数量为:" << arr1.get_Size() << endl;
printArr<int> (arr1, arr1.get_Size());
}
void test02(){
MyArray<Person> arr(10);
Person p1("猴哥儿", 1000);
Person p2("八戒", 700);
Person p3("沙师弟", 200);
Person p4("师傅", 20);
Person p5("菩萨", 10000);
arr.Push_Back(p1);
arr.Push_Back(p2);
arr.Push_Back(p3);
arr.Push_Back(p4);
arr.Push_Back(p5);
cout << "arr的容量为:" << arr.get_Capacity() << endl;
cout << "arr的元素数量为:" << arr.get_Size() << endl;
printUdfArr(arr);
}
int main(){
// test01();
test02();
}
网友评论