2016-12-22 2 views
0

2つのベクトルが互いに比較され、ベクトルからの差の2乗の和が求められます。私は昇順で値をソートしようとしたとき、私は平方差分値の和のすべてを表示することができC++ポインタ配列をソート順にソート

double Search::NNS(vector<vector<double>> bb, vector<vector<double>> aa) 
    { 
     int M = 768; int N = 1024; 
     int R = 49; int C = 36; 
     //double SSD[] = MainVectorBlock[] - WallyVector[]; 
     //double SSD[] = SSD[] * SSD[]; 
     //sum = sum + SSD[]; 

    vector<vector<double>> &MainIMG = bb; 
    vector<vector<double>> &WallyIMG = aa; 
    double *SSD = new double[R*C]; 
    double sum = 0; 


    for (int bx = 0; bx < M; bx += R) 
     for (int by = 0; by < N; by += C) 
     { 
      Compare = new double*[R]; 
      for (int x = 0; ((x < R) && ((bx + x) < M)); ++x) 
      { 
       Compare[x] = new double[R]; 
       for (int y = 0; ((y < C) && ((by + y) < N)); ++y) 
       { 
        if ((bx + x) >= M) 
        { 
         cout << Compare[bx + x] << Compare[by + y] << " "; 

        } 

        //cout << MainIMG[bx + x][by + y] << " "; 
        Compare[x][y] = MainIMG[bx + x][by + y] - WallyIMG[x][y]; 
        Compare[x][y] = Compare[x][y] * Compare[x][y]; 
        //sum += Compare[x][y]; 
        SSD[R*C] += Compare[x][y]; 
        //SSD[R*C] = sum; 
        //cout << Compare[x][y] << " "; 
       } 

      } 
      //cout << "\n\n\n" << endl; 
      //cout << sum << endl; 
      //cout << SSD[R*C] << "\t" << sum << endl; 

      for (int i = 0; i < R*C; i++) 
      { 
       for (int j = 0; j < R*C; j++) 
       { 
        if (SSD[i] > SSD[j]) 
        { 
         int temp = SSD[i]; 
         SSD[i] = SSD[j]; 
         SSD[j] = temp; 
        } 
       } 
      } 

     } 
    for (int a = 0; a < R*C; a++) 
    { 
     cout << SSD[a] << endl; 
    } 

    return 0; 
} 

は、しかし、私は、この値-6.27744e + 66を得ることに保ちます。 私はループを変更して、それをメインfor-loop全体に配置しようとしましたが、私はまだその値を得続けています。

+1

このような問題を解決する適切なツールは、デバッガです。スタックオーバーフローを尋ねる前に、コードを一行ずつ進める必要があります。詳しいヘルプは、[小さなプログラムをデバッグする方法(Eric Lippert)](https://ericlippert.com/2014/03/05/how-to-debug-small-programs/)を参照してください。最低でも、あなたはあなたが行った観察と一緒に、[編集]あなたの質問あなたの問題を再現[、最小完全、かつ検証](http://stackoverflow.com/help/mcve)の例を含むようにする必要があります\しますデバッガ。 –

+0

-6.27744e + 66は私に二重の浮動小数点のように見えます。あなたは配列の範囲内の要素を常に読んでいるのですか? – Bathsheba

+0

@πάνταῥεῖデバッガを使いましたが、なぜこれが起きているのかまだ分かりません。 – MR1

答えて

1
double *SSD = new double[R*C]; 

あなたはメモリを割り当てていますが、それを何らかの値に初期化したことはありません。そして、あなたはそれを直接使用しています

SSD[R*C] += Compare[x][y]; 

はそれに値を追加する開始する前SSD0への全項目を初期化します。

0

コードに複数の問題があります。

  1. 彼らはconst参照によって渡されるべきときは、NNS関数に値によって、2Dベクトルを渡しています。
  2. ネストされたforループ内でメモリリークを作成しています。
  3. 合計計算で配列SSDの末尾を1つ書きます。
  4. はあなたのSSDアレイはここでメモリリークを持っていないあなたの関数のバージョンがあり、そしてあなたは、上記の)項目3に対処できるようになります0

に初期化されていませんでした。これを改善することができますが、上記の問題はありません。

#include <vector> 
#include <iostream> 
#include <algorithm> 

double Search::NNS(const std::vector<std::vector<double>>& bb, 
        const std::vector<std::vector<double>>& aa) 
{ 
    int M = 768; int N = 1024; 
    int R = 49; int C = 36; 
    const std::vector<std::vector<double>> &MainIMG = bb; 
    const std::vector<std::vector<double>> &WallyIMG = aa; 
    std::vector<double> SSD(R * C); 
    double sum = 0; 

    for (int bx = 0; bx < M; bx += R) 
    { 
     for (int by = 0; by < N; by += C) 
     { 
      std::vector<std::vector<double>> Compare(R, std::vector<double>(R)); 
      for (int x = 0; ((x < R) && ((bx + x) < M)); ++x) 
      { 
       for (int y = 0; ((y < C) && ((by + y) < N)); ++y) 
       { 
        Compare[x][y] = MainIMG[bx + x][by + y] - WallyIMG[x][y]; 
        Compare[x][y] = Compare[x][y] * Compare[x][y]; 
        SSD.at(R*C) += Compare[x][y]; 
       } 
      } 
     } 
    } 
    std::sort(SSD.begin(), SSD.end()); 
    for (int a = 0; a < R*C; a++) 
     std::cout << SSD[a] << std::endl; 
    return 0; 
} 

問題1)は、vectorをconst参照で渡すことによって対処されます。オリジナルのコードが実行していたときにベクターの値を渡すと、不要なコピーが発生します。

問題2)は、の代わりにnew[]を使用して解決します。今やメモリリークはありません。

3)は、であり、は直接扱われません。行われたことは、範囲外の状態が発生していることを示すためにstd::vector::at()を使用することでした。 at()が使用されているときに境界外に出ると、配列へのアクセスにエラーがあることを示す例外がスローされます(std::out_of_range)。その行が実行されるとすぐにコードが停止してしまいます。ここで境界条件を解決するために私はそれをあなたに任せます。

Compareベクターでat()を使用して、範囲外にならないようにすることもできます。私は怠惰で、私の頭の中で計算をしたくないのですが、forのループ条件では、制限条件としてvector::size()を使用せず、代わりにどのくらいループするかを判断するために疑わしい境界外の状況が発生する可能性があります。

また、new[]を使用した場合、このエラーが発生する保証はなく、何か間違ったことを示しているわけではありません。 std::vectorを使用すると、at()を使用して境界条件を確認できます。

発行4)は、デフォルトでとして、std::vector<double>を使用することによって対処され、ベクトルの範囲はなく、遅いバブルソートをソートするstd::sortの使用に注意し、0

最後まで内容を初期化します。

+0

メモリリークについて教えてくれてありがとう、私はそれに取り組むでしょう。再び乾杯 – MR1