C++ 有没有办法绕开;返回对局部变量的引用;问题
我有一个家庭作业练习。我几乎可以肯定,按照他们的要求,这是无法解决的。然而,我很感兴趣的是,你们是否有任何解决下面提到的问题的方法,因为这似乎是经常发生的事情 描述不长,因此我在下面与您分享: 矩阵∈ rn×n是斜对称的,如果它保持S(转置)= −从课堂上的讲课中推导出平方矩阵 斜对称矩阵。使用长度为n(n)的向量− 1) /2以存储 矩阵条目。实施施工人员、类型铸造和适当的 访问系数 问题发生在尝试提供访问时,因为SquareMatrix中定义的虚拟访问方法返回一个引用C++ 有没有办法绕开;返回对局部变量的引用;问题,c++,C++,我有一个家庭作业练习。我几乎可以肯定,按照他们的要求,这是无法解决的。然而,我很感兴趣的是,你们是否有任何解决下面提到的问题的方法,因为这似乎是经常发生的事情 描述不长,因此我在下面与您分享: 矩阵∈ rn×n是斜对称的,如果它保持S(转置)= −从课堂上的讲课中推导出平方矩阵 斜对称矩阵。使用长度为n(n)的向量− 1) /2以存储 矩阵条目。实施施工人员、类型铸造和适当的 访问系数 问题发生在尝试提供访问时,因为SquareMatrix中定义的虚拟访问方法返回一个引用 const doubl
const double& SquareMatrix::operator()( int j, int k ) const
{
assert( j >= 0 && j < m );
assert( k >= 0 && k < n );
return coeff[ j + k * m ];
}
常量double&SquareMatrix::operator()(int j,int k)常量
{
断言(j>=0&&jconst double& SkewSymmetricMatrix::operator()( int j, int k ) const
{
assert( j >= 0 && j < size() );
assert( k >= 0 && k < size() );
if( j < k )
{
const double* coeff = getCoeff();
return coeff[ j * ( j - 1 ) / 2 + k ];
}
else if ( j > k )
{
const double* coeff = getCoeff();
return -coeff[ k * ( k - 1 ) / 2 + j ];
}
else
{
return const_zero;
}
}
常量double&SkewSymmetricMatrix::operator()(int j,int k)常量
{
断言(j>=0&&j如果您希望
constdouble&SquareMatrix::operator()(intj,intk)const{…}
重写一个虚方法,从而不断返回一个constdouble&
,那么我不知道怎么做
如果允许您更改签名,则创建
class ValueAccessor {
double &value;
bool is_negated;
public:
ValueAccessor& operator=(double other) {
value = is_negated ? -other : other;
return *this;
}
operator double() const {
return is_negated ? -value : value;
}
...
};
,并从
operator()(…)
返回ValueAccessor
。问题需要使用n*(n-1)/2
元素的向量,但它没有指定该向量应包含的元素类型
矩阵∈ 如果R n×n保持S(转置)=−从课堂上的SquareMatrix类派生出SkewSymmetricMatrix类。使用长度为n(n)的向量− 1) /2以存储矩阵项。执行构造函数、类型转换和适当访问系数
考虑到我们没有能力更改SquareMatrix
类给出的接口,我们将不得不求助于用技术上符合要求的解决方案来解决这个问题,即使它不符合教授要求的精神(这是不可能的)
向量的每个元素将包含两个双
值,一个对应于元素m_ij
,另一个对应于m_ji
(对于i
)。我们可以称之为左元素和右元素:
struct mirror {
double left;
double right;
void assignLeft(double val) {
left = val;
right = -val;
}
void assignRight(double val) {
left = -val;
right = val;
}
};
我们可以使用类型为mirror
的n*(n-1)/2
元素的向量,并根据请求的索引返回左
或右
成员:
const double& SkewSymmetricMatrix::operator()( int j, int k ) const
{
assert( j >= 0 && j < size() );
assert( k >= 0 && k < size() );
if( j < k )
{
const mirror* coeff = getCoeff();
return coeff[ j * ( j - 1 ) / 2 + k ].left;
}
else if ( j > k )
{
const mirror* coeff = getCoeff();
return coeff[ k * ( k - 1 ) / 2 + j ].right;
}
else
{
return const_zero;
}
}
常量double&SkewSymmetricMatrix::operator()(int j,int k)常量
{
断言(j>=0&&j莫斯科就是这样。评论中的一个想法是使用临时私人会员并返回对其的引用。那真是个坏主意: 如果使用对私有成员的引用,则该值将在下次调用时更改。如果调用方使用:
const double& val1 = my_square_matrix(2, 1);
const double& val2 = my_square_matrix(3, 1);
double sum = val1 + val2;
结果将是val2+val2
,而不是val1+val2
,因为引用了错误的值
但是有两种解决方案可以满足要求:
在许多现代64位系统上,
double&
使用的内存量与double
相同,因此复制double
在速度和内存使用方面都很好。但是,如果希望调用方能够修改值,则需要返回一个double&
。解决方法是返回一个值,而不是一个引用。将计算值存储在私有类成员中,然后返回对它的引用。@SamVarshavchik:通过将计算值存储在私有类成员中,这将无法按预期工作:my_square_矩阵(2,1)=42
@pts这是一个常量引用。这不起作用,因为该类正在重写另一个类中的虚拟方法,并且提问者无法控制基类方法的签名。除非试图证明设计拙劣的缺陷,否则我永远不会分配这样的问题。如果我分配了这样一个问题,这个解决方案将被标记为不正确,因为它是我的