2016-07-22 11 views
0

私はthisの記事の後にC++でSIFTRootを実装しようとしています。特にOpenCV:記述子行列のL1正規化

# apply the Hellinger kernel by first L1-normalizing and taking the 
    # square-root 
    descs /= (descs.sum(axis=1, keepdims=True) + eps) 
    descs = np.sqrt(descs) 

私の質問は以下のとおりです。

  1. は、OpenCVの中でこれを行うには任意の組み込みのC++の機能はありますか?
  2. すべての記述子が正の値ですか?それ以外の場合、L1ノルムは各要素のabsを使用する必要があります。
  3. 最初の行は、 "各行ベクトルに対して、すべての要素の合計を計算した後、eps(0で除算しないように)を追加し、最後に各ベクトル要素をこの合計値で除算します。

答えて

1

SIFT記述子は基本的にヒストグラムなので、負の値を持つべきではありません。私はあなたが達成したいことをOpenCVの一つの機能が存在するとは思わない。しかし、それは仕事

// For each row 
for (int i = 0; i < descs.rows; ++i) { 
    // Perform L1 normalization 
    cv::normalize(descs.row(i), descs.row(i), 1.0, 0.0, cv::NORM_L1); 
} 
// Perform sqrt on the whole descriptor matrix 
cv::sqrt(descs, descs); 

を行い数行を思い付くには余りにも難しいことではありません、私は正確にどのようにOpenCVの取引L1の正規化でゼロ合計が分かりません。上記のコードでNaNが生成された場合は、cv::normalizedescs.rows(i) /= (cv::norm(descs.rows(i), cv::NORM_L1) + eps)に置き換えることができます。

+0

ありがとう、私はちょうど 'cv :: normalize'がどのように動作するのか理解しようとしていましたが、ドキュメントの' alpha 'で混乱しました。ありがとう! – justHelloWorld