一、 构造函数
1. CMatrix(): 不带参数的构造函数
CMatrix::CMatrix()
{
m_nRow = 0;
m_nCol = 0;
*m_pData = NULL;
}
2. 带行、列及数据指针等参数的构造函数,并且参数带默认值
CMatrix::CMatrix(int nRow, int nCol, double *pData) : m_pData(0)
{
Create(nRow, nCol, pData);
}
3. 带文件路径参数的构造函数
CMatrix::CMatrix(const char * strPath)
{
m_pData = 0;
m_nRow = m_nCol = 0;
ifstream cin(strPath); //从硬盘到文件的输入流
cin >> *this;
}
4. 拷贝构造函数
CMatrix::CMatrix(const CMatrix& m):CMatrix(m.m_nRow, m.m_nCol, m.m_pData)
{
m.m_pData = NULL;
*this = m;
}
5. 用列表初始化成员变量
CMatrix::CMatrix():m_nRow(0),m_nCol(0),m_pData(NULL)
{
}
*6. bool Create(int nRow, int nCol, double pData=NULL): 先删除原有空间,根据传入行列创建空间,如果pData不为空要将pData的内容拷贝到m_pData中
bool CMatrix::Create(int nRow, int nCol, double *pData)
{
Release();
m_pData = new double[nRow*nCol];
m_nRow = nRow;
m_nCol = nCol;
if (pData != NULL and m_pData != NULL)
{
memcpy(m_pData, pData, nRow*nCol * sizeof(double));
return true;
}
return false;
}
二、析构函数
1.~ CMatrix(): 调用Release()
CMatrix::~CMatrix()//析构函数重载释放空间
{
Release(); //调用函数进行释放空间
}
2. Release(): 将内存释放,并将行列设置为0
void CMatrix::Release()
{
if (m_pData)
{
delete[]m_pData;
m_pData = NULL;
}
m_nRow = m_nCol = 0;
}
三、运算符重载
1. 算术运算符重载:+, -, +=, -=
//加法
CMatrix& CMatrix::operator+(const CMatrix& m) //一个参数
{
assert(m_nRow==m.m_nRow && m_nCol==m.m_nCol);
for(int i=0;i<m_nRow*m_nCol;i++)
{
m_pData[i]+=m.m_pData[i];//对结果进行相加
}
return *this;
}
CMatrix operator+(const CMatrix& m1, const CMatrix& m2) //两个参数
{
CMatrix m3(m1); //拷贝构造函数
m3 += m2;
return m3;
}
//减法
CMatrix& CMatrix::operator-(const CMatrix& m){ //一个参数
assert(m_nRow==m.m_nRow && m_nCol==m.m_nCol);
for(int i = 1;i < m_nRow*m_nCol; i++){
m_pData[i] -= m.m_pData[i];
}
return *this;
}
//+=
CMatrix& CMatrix::operator+=(const CMatrix& m){
assert(m_nRow==m.m_nRow && m_nCol==m.m_nCol);
for(int i = 1;i < m_nRow*m_nCol; i++){
m_pData[i] += m.m_pData[i];
}
return *this;
}
//-=
CMatrix& CMatrix::operator-=(const CMatrix& m){
assert(m_nRow==m.m_nRow && m_nCol==m.m_nCol);
for(int i = 1;i < m_nRow*m_nCol; i++){
m_pData[i] -= m.m_pData[i];
}
return *this;
2. 关系运算符重载:>, <, ==,!=
//>大于号
//结果返回一个布尔值
bool CMatrix::operator >(const CMatrix& m){
assert(m_nRow==m.m_nRow && m_nCol==m.m_nCol);
for(int i = 1;i < m_nRow*m_nCol; i++){
if(m_pData[i] > m.m_pData[i])
return true;;
}
return false;
}
//<小于号
//结果返回一个布尔值
bool CMatrix::operator <(const CMatrix& m){
assert(m_nRow==m.m_nRow && m_nCol==m.m_nCol);
for(int i = 1;i < m_nRow*m_nCol; i++){
if(m_pData[i] < m.m_pData[i])
return true;;
}
return false;
}
//==等于
//结果返回一个布尔值
bool CMatrix::operator ==(const CMatrix& m){
if(!(m_nRow==m.m_nRow && m_nCol==m.m_nCol))
return false;
for(int i = 1;i < m_nRow*m_nCol; i++){
if(m_pData[i] != m.m_pData[i])
return false;;
}
return true;
}
// != 不等于
//结果返回一个布尔值
bool CMatrix::operator !=(const CMatrix& m){
return !(*this == m);
}
3. 下标操作符:[], ()
//[]
double & CMatrix::operator[](int nIndex)
{
assert(nIndex < m_nRow*m_nCol); //确保不溢出
return m_pData[nIndex];
}
//()
double & CMatrix::operator()(int nRow, int nCol)
{
assert(nRow*m_nCol + nCol < m_nRow*m_nCol);
return m_pData[nRow*m_nCol + nCol];
}
4. 强制类型转换: double
//强制类型转换
CMatrix::operator double() //返回总和
{
double dS = 0;
for (int i = 0; i < m_nRow*m_nCol; i++)
{
dS += m_pData[i];
}
return dS;
}
5. 赋值运算符:=,尤其注意当m1=m1特殊情况的处理
//=符值
CMatrix & CMatrix::operator=(const CMatrix& m)
{
if (this != &m) {
Create(m.m_nRow, m.m_nCol, m.m_pData);
}
return *this;
}
四、友元函数
1. 输入和输出运输符:<<, >>
//输入>>
istream & operator>>(istream& is, CMatrix & m)
{
is >> m.m_nRow >> m.m_nCol;
m.Create(m.m_nRow, m.m_nCol);
for (int i = 0; i < m.m_nRow*m.m_nCol; i++)
{
is >> m.m_pData[i];
}
return is;
}
//输出<<
ostream & operator<<(ostream& os, const CMatrix &m)
{
os << m.m_nRow << " " << m.m_nCol << endl;
double * pData = m.m_pData;
for (int i = 0; i < m.m_nRow; i++)
{
for (int j = 0; j < m.m_nCol; j++)
{
os << *pData++ << " ";
}
os << endl;
}
return os;
}
五、实验总结
- 通过本次实验学习了几种构造函数、析构函数、友元函数及各类运算符的重载。虽在此之前学过Java,对类和对象有一定的理解,但对有些函数的构造重载还是不熟练,此次实验对每个函数进行梳理并多敲了几遍,对该模块知识点有了更深刻的理解,希望以后能多将此块知识运用于实践。