2

多くの例/チュートリアルで、マトリックスアクセスに中括弧演算子「()」を使用していることに気づきました。これは、場合によっては混乱を招きます。

問題は次のとおりです。Mという名前の*m行列(たとえば、3x4)があるとします。「M(0)」、「M(1)」、またはその他の特異なパラメーターを介してアクセスすると、どの要素が返されますか。中かっこの中?行と列の両方を指定することになっていると思いました(「M(0,1)」など)。

4

2 に答える 2

7

線形インデックスアクセスがあります。つまり、線形の方法でメモリに直接アクセスします。

マトリックスでは、すべての要素が1つの大きなメモリブロックに格納され、各行は前の行の後に続きます。(i, j)これが、あなたが書く位置にある要素にアクセスしたい場合、次のように考える理由です。

elem = matrix(j + rowWidth*i)

しかし、あなたは単にそれにアクセスすることができます

elem = matrix(k)

これは、行/列の位置を気にしない場合、たとえば、マトリックス内のすべての要素を合計する場合に役立ちます。

count = width*height;
sum=0;
for(i=0;i<count;i++)
    sum+=matrix(i);

または、線形インデックスを事前に計算した場合。

マトリックスがメモリの連続ブロックに格納されていない場合、この手法では最もクレイジーなバグが発生する可能性があることに注意してください。たとえば、より大きなマトリックスの関心領域などです。if (myMat.isContinuous())線形インデックスを使用する前に必ず確認してください。

于 2012-07-30T09:05:38.477 に答える
0

これはOpenCV2.4.2からのものです

template<typename _Tp> inline _Tp& Mat_<_Tp>::operator ()(int i0, int i1)
{
    return ((_Tp*)(data + step.p[0]*i0))[i1];
}
template<typename _Tp> inline _Tp& Mat_<_Tp>::operator ()(int i0)
{
    return this->at<_Tp>(i0);
}
template<typename _Tp> inline _Tp& Mat_<_Tp>::operator ()(int i0, int i1, int i2)
{
    return this->at<_Tp>(i0, i1, i2);
}

Mat::at(int i0)これはMat_公に継承する定義ですMat

template<typename _Tp> inline const _Tp& Mat::at(int i0) const
{
    if( isContinuous() || size.p[0] == 1 )
        return ((const _Tp*)data)[i0];
    if( size.p[1] == 1 )
        return *(const _Tp*)(data + step.p[0]*i0);
    int i = i0/cols, j = i0 - i*cols;
    return ((const _Tp*)(data + step.p[0]*i))[j];
}
于 2012-08-01T07:04:30.163 に答える