在矩阵实现的[]运算符中查找设计缺陷 在C++程序中,这里有两个操作符标题作为未显示的矩阵实现的设置器和吸气剂。p> double* Matrix::operator[](unsigned int row) const throw (MatrixException); double* Matrix::operator[](unsigned int row) throw (MatrixException);

在矩阵实现的[]运算符中查找设计缺陷 在C++程序中,这里有两个操作符标题作为未显示的矩阵实现的设置器和吸气剂。p> double* Matrix::operator[](unsigned int row) const throw (MatrixException); double* Matrix::operator[](unsigned int row) throw (MatrixException);,c++,pointers,matrix,C++,Pointers,Matrix,在不进一步了解上述运算符的实现情况的情况下,仅通过查看如何定义上述运算符,如果实现这两种方法,矩阵程序中的设计缺陷将是什么 关于[]操作员如何工作的澄清: 矩阵设置如下: Matrix *a = new Matrix(1,2); //matrix with one row and two columns a[0][0] = 3.0; a[0][1] = 2.3; //to access a matrix value double* b = a[0][1]; delete a; 编辑:为了修

在不进一步了解上述运算符的实现情况的情况下,仅通过查看如何定义上述运算符,如果实现这两种方法,矩阵程序中的设计缺陷将是什么

关于[]操作员如何工作的澄清: 矩阵设置如下:

Matrix *a = new Matrix(1,2); //matrix with one row and two columns
a[0][0] = 3.0; 
a[0][1] = 2.3;

//to access a matrix value
double* b = a[0][1];
delete a;

编辑:为了修复设计缺陷,您会在操作符定义中更改什么?

第一个设计缺陷是使用异常规范,在C++11中已弃用

第二个设计缺陷是,您可以在行列之外建立索引,而类无法对此进行检查。即

Matrix a( 1, 2 );
double b = a[0][4];
使用代理可以进行边界检查

最后,你的例子完全是假的。您将
a
声明为指针,因此在下标
a[0][0]
时,实际上是先下标指针,然后下标行。

存在一些缺陷

最明显的是不必要地使用带有手动内存管理的动态内存。每当你看到
delete
时,你几乎知道有什么地方出了问题,而每当你看到
new
时,你都应该心存怀疑

Matrix a(1, 2); // no new needed
a[0][0] = 3.0;
a[0][1] = 2.3;
double * b = a[0][1];
// no delete needed
这可以完全防止内存泄漏。它还避免了您包含的错误,即没有实际索引数组(您需要使用
(*a)[0][0]
来获取第一个元素)

其次,应该返回对值的引用,而不是指针

第三,您应该创建一个返回值并将两个索引作为参数的函数,而不是重载
运算符[]
,以返回一个数组,然后必须再次取消引用该数组

这允许您检查边界,假设
矩阵
知道它自己的大小(它必须存储两个整数数据成员)

double&
版本中有一个明显的实现。目前,您的
const
成员函数版本返回一个
double*
,而不是通过返回
double const*
使
const
可传递(尽管仍然首选引用)

另一个潜在缺陷是,像
矩阵
这样的泛型类可能应该在类型上参数化:

template<typename T>
class Matrix {
public:
    typedef T value_type;
    ...
};
模板
类矩阵{
公众:
类型定义T值_类型;
...
};
因此,您的示例实际上将使用
矩阵
作为类型


最后,我要对异常规范说不。它们往往会导致比修复的错误更多的错误,这就是为什么它们在C++11中被弃用的原因。

对于初学者,它们应该返回引用,而不是指针。此外,异常规范(函数旁边的“throw”)已被弃用。像这样的throw规范令人困惑、误导,并且已从c++11中删除(弃用)。很好的删除如何修改运算符定义以检查边界?
double const & Matrix::at(size_t const row, size_t const column) const {
    check_bounds(row, column);
    return implementation_detail();
}
template<typename T>
class Matrix {
public:
    typedef T value_type;
    ...
};