Как вычислить обратное Фурье, используя FFTW - PullRequest
0 голосов
/ 03 октября 2019

В настоящее время я занят изучением использования преобразования Фурье при обработке изображений в C ++ (Qt). Я создал программу для вычисления прямого преобразования Фурье изображения в градациях серого. Моя цель сейчас - просто определить обратное число Фурье, чтобы получить исходное изображение (лена). Найдите ниже код для прямого Фурье.

    QImage original_image;
    original_image.load(":/pic22.png");
    original_image= original_image.scaled(ui->img_label_1->size());

    //Compute grayscale
    QImage gray(ui->img_label_1->size(), QImage::Format_ARGB32); // a new image with the same size
    double gray_img[gray.width()][gray.height()]; //this is a matrix for pixel values
    for (int row = 0; row < original_image.height(); ++row)
    {
      for (int col = 0; col < original_image.width(); ++col)
      {
        auto color = original_image.pixelColor(col, row);
        auto r = color.red();
        auto g = color.green();
        auto b = color.blue();
        auto gr = (r+g+b)/3;

        gray.setPixelColor(col, row, QColor(gr, gr,gr, gr > 0 ? color.alpha() : 0));
        gray_img[row][col]=gr;
      }
    }

    ui->img_label_1->setPixmap(QPixmap::fromImage(gray));

    //Setup the fourier functions
    fftw_complex *in, *out;
    fftw_plan g;

    in = (fftw_complex *)fftw_malloc(sizeof(fftw_complex) * original_image.width()*original_image.height());
    out = (fftw_complex *)fftw_malloc(sizeof(fftw_complex) * original_image.width()*original_image.height());

    g = fftw_plan_dft_2d(original_image.width(), original_image.height(), in, out, FFTW_FORWARD, FFTW_ESTIMATE);
    //Transform 2d array into 1d

    int dummy = 0;
    for (int x = 0; x< original_image.width() ; x++)
    {
        for (int y = 0; y< original_image.height(); y++)
        {
            in[dummy][0]=gray_img[x][y]; //set real equal to pixel
            in[dummy][1]=0; //set complex == 0
            dummy++;
        }
    }


    //Compute the fourier
     fftw_execute(g);

     dummy = 0;
     for (int x = 0; x< original_image.width() ; x++)
     {
         for (int y = 0; y< original_image.height(); y++)

         {
            fourier_raw[x][y][0] = out[dummy][0];
            fourier_raw[x][y][1] = out[dummy][1];
            dummy++;
         }
     }

Затем я беру выходные данные этого фурье и "красиво печатаю" их в амплитудные и фазовые графики. Величина и фаза на выходе правильные, это я могу подтвердить. Однако когда я беру эти значения и пытаюсь найти обратное fft, я получаю огромные выходные значения как для вещественных, так и для сложных частей.

//Create local fourier copy
    float local_fourier[250][250][2];
    float local_iff[250][250][2];

    for (int x = 0; x < ui->img_label_1->width()/2; x++)
    {
         for (int y = 0; y <  ui->img_label_1->height()/2; y++)
         {
            local_fourier[x][y][0] = fourier_raw[x][y][0];
            local_fourier[x][y][1] = fourier_raw[x][y][1];
         }
    }

    //Setup the fourier functions
    fftw_complex *in, *out;
    fftw_plan g;

    in = (fftw_complex *)fftw_malloc(sizeof(fftw_complex) * ui->img_label_1->width()*ui->img_label_1->height());
    out = (fftw_complex *)fftw_malloc(sizeof(fftw_complex) * ui->img_label_1->width()*ui->img_label_1->height());

    g = fftw_plan_dft_2d(ui->img_label_1->width(), ui->img_label_1->height(), in, out, FFTW_BACKWARD, FFTW_ESTIMATE);

    //Transform 2d array into 1d

    int dummy = 0;
    for (int x = 0; x< ui->img_label_1->width() ; x++)
    {
        for (int y = 0; y< ui->img_label_1->height(); y++)
        {
            in[dummy][0]=local_fourier[x][y][0]; //set real equal to original fourier
            in[dummy][1]=local_fourier[x][y][1]; //set complex equal to original fourier
            dummy++;
        }
    }


    //Compute the fourier
     fftw_execute(g);

     dummy = 0;
     for (int x = 0; x< ui->img_label_1->width() ; x++)
     {
         for (int y = 0; y< ui->img_label_1->height(); y++)

         {
            local_iff[x][y][0] = out[dummy][0];
            local_iff[x][y][1] = out[dummy][1];
            dummy++;
            std::cout<<"R: "<< local_iff[x][y][0] << " C: "<<local_iff[x][y][1]<<std::endl;
         }
     }

Приведенный выше код - это место, где я пытаюсь найти обратное fft. Ниже приведены некоторые из полученных выходных значений.

R: 1.27403e+26 C: -1.40704e+26
R: -1.24615e+26 C: -1.09294e+26
R: -8.89592e+25 C: 1.12468e+26
R: 1.04593e+26 C: 6.72015e+25
R: 4.48723e+25 C: -1.01163e+26
R: -1.02188e+26 C: -2.28396e+25
R: -1.95695e+24 C: 1.07515e+26
R: 1.16831e+26 C: -1.69667e+25
R: -3.3196e+25 C: -1.29678e+26
R: -1.45467e+26 C: 4.60953e+25
R: 5.51512e+25 C: 1.63501e+26
R: 1.82997e+26 C: -5.99914e+25
R: -6.03974e+25 C: -2.03117e+26
R: -2.22995e+26 C: 5.63127e+25
R: 4.7845e+25 C: 2.41769e+26
R: 2.58614e+26 C: -3.52622e+25
R: -1.89834e+25 C: -2.72769e+26
R: -2.83563e+26 C: -4.36023e+23
R: -2.23241e+25 C: 2.90441e+26
R: 2.92986e+26 C: 4.59158e+25
R: 7.03802e+25 C: -2.90928e+26
R: -2.84159e+26 C: -9.48495e+25
R: -1.1845e+26 C: 2.72736e+26
R: 2.56877e+26 C: 1.40334e+26
R: 1.59707e+26 C: -2.36956e+26
R: -2.13489e+26 C: -1.75858e+26
R: -1.88186e+26 C: 1.87117e+26
R: 1.58579e+26 C: 1.96216e+26
R: 1.99624e+26 C: -1.28694e+26
R: -9.83243e+25 C: -1.98238e+26
R: -1.92055e+26 C: 6.83515e+25
R: 3.96411e+25 C: 1.81234e+26
R: 1.66091e+26 C: -1.30141e+25
R: 1.07821e+25 C: -1.4709e+26
R: -1.24828e+26 C: -3.11003e+25
R: -4.74157e+25 C: 1.00009e+26
R: 7.34226e+25 C: 5.93446e+25
R: 6.66576e+25 C: -4.59154e+25
R: -1.83609e+25 C: -6.92877e+25
R: -6.73321e+25 C: -8.37101e+24
R: -3.34453e+25 C: 6.10488e+25
R: 5.08472e+25 C: 5.6091e+25
R: 7.56284e+25 C: -3.72732e+25
R: -2.09899e+25 C: -9.1493e+25
R: -1.03256e+26 C: 2.75374e+24
R: -1.66126e+25 C: 1.10637e+26
R: 1.13518e+26 C: 3.62493e+25
R: 5.52903e+25 C: -1.11943e+26
R: -1.0612e+26 C: -7.28939e+25
R: -8.82731e+25 C: 9.641e+25
R: 8.33176e+25 C: 1.00723e+26
R: 1.09648e+26 C: -6.74699e+25
R: -4.9596e+25 C: -1.14579e+26
R: -1.15195e+26 C: 3.04999e+25
R: 1.10328e+25 C: 1.11332e+26
R: 1.02987e+26 C: 7.93826e+24
R: 2.55604e+25 C: -9.03228e+25
R: -7.36601e+25 C: -4.10261e+25
R: -5.36012e+25 C: 5.34654e+25
R: 3.03357e+25 C: 6.26522e+25
R: 6.76676e+25 C: -4.97738e+24
R: 2.1819e+25 C: -6.82776e+25
R: -6.42664e+25 C: -4.92065e+25
R: -7.63116e+25 C: 5.55805e+25
R: 4.23309e+25 C: 1.02265e+26
R: 1.26233e+26 C: -2.47891e+25
R: -3.37804e+24 C: -1.47446e+26
R: -1.65227e+26 C: -2.13428e+25
R: -4.8697e+25 C: 1.79013e+26
R: 1.88379e+26 C: 7.79149e+25
R: 1.0816e+26 C: -1.93048e+26
R: -1.92905e+26 C: -1.38561e+26
R: -1.68237e+26 C: 1.88001e+26
R: 1.78547e+26 C: 1.96335e+26
R: 2.22056e+26 C: -1.64909e+26
R: -1.47599e+26 C: -2.44681e+26
R: -2.63603e+26 C: 1.2725e+26
R: 1.04597e+26 C: 2.78343e+26
R: 2.88566e+26 C: -8.04524e+25
R: -5.56738e+25 C: -2.94096e+26
R: -2.94923e+26 C: 3.1137e+25
R: 7.7029e+24 C: 2.91196e+26
R: 2.83226e+26 C: 1.38119e+25
R: 3.26645e+25 C: -2.71471e+26
R: -2.56516e+26 C: -4.82116e+25
R: -5.99321e+25 C: 2.3906e+26
R: 2.19884e+26 C: 6.74458e+25
R: 7.05266e+25 C: -1.99826e+26
R: -1.79752e+26 C: -6.91102e+25
R: -6.32966e+25 C: 1.60524e+26
R: 1.42967e+26 C: 5.33459e+25
R: 3.96696e+25 C: -1.27846e+26
R: -1.15831e+26 C: -2.28154e+25
R: -3.44753e+24 C: 1.07477e+26
R: 1.03207e+26 C: -1.76764e+25
R: -3.97327e+25 C: -1.0329e+26
R: -1.07837e+26 C: 6.18614e+25
R: 8.3196e+25 C: 1.16795e+26
R: 1.29949e+26 C: -1.02895e+26
R: -1.20172e+26 C: -1.46927e+26
R: -1.67218e+26 C: 1.34323e+26
R: 1.44753e+26 C: 1.90186e+26
R: 2.15093e+26 C: -1.50995e+26
R: -1.52729e+26 C: -2.41128e+26
R: -2.6743e+26 C: 1.49792e+26
R: 1.42185e+26 C: 2.93126e+26
R: 3.17354e+26 C: -1.30073e+26
R: -1.1378e+26 C: -3.39299e+26
R: -3.58218e+26 C: 9.37736e+25
R: 7.06559e+25 C: 3.73472e+26
R: 3.84542e+26 C: -4.51363e+25
R: -1.80094e+25 C: -3.91049e+26
R: -3.92772e+26 C: -9.87352e+24
R: -3.76347e+25 C: 3.8965e+26
R: 3.81788e+26 C: 6.44003e+25
R: 8.93315e+25 C: -3.69451e+26
R: -3.53054e+26 C: -1.11654e+26
R: -1.30684e+26 C: 3.33153e+26
R: 3.10418e+26 C: 1.45854e+26
R: 1.56734e+26 C: -2.85612e+26
R: -2.59567e+26 C: -1.6304e+26
R: -1.64651e+26 C: 2.33149e+26
R: 2.07235e+26 C: 1.61612e+26
R: 1.54126e+26 C: -1.82673e+26
R: -1.60258e+26 C: -1.42556e+26
R: -1.27403e+26 C: 1.40704e+26
R: 1.24615e+26 C: 1.09294e+26
R: 8.89592e+25 C: -1.12468e+26
R: -1.04593e+26 C: -6.72015e+25
R: -4.48723e+25 C: 1.01163e+26
R: 1.02188e+26 C: 2.28396e+25
R: 1.95695e+24 C: -1.07515e+26
R: -1.16831e+26 C: 1.69667e+25
R: 3.3196e+25 C: 1.29678e+26
R: 1.45467e+26 C: -4.60953e+25
R: -5.51512e+25 C: -1.63501e+26
R: -1.82997e+26 C: 5.99914e+25
R: 6.03974e+25 C: 2.03117e+26
R: 2.22995e+26 C: -5.63127e+25
R: -4.7845e+25 C: -2.41769e+26
R: -2.58614e+26 C: 3.52622e+25
R: 1.89834e+25 C: 2.72769e+26
R: 2.83563e+26 C: 4.36023e+23
R: 2.23241e+25 C: -2.90441e+26
R: -2.92986e+26 C: -4.59158e+25
R: -7.03802e+25 C: 2.90928e+26
R: 2.84159e+26 C: 9.48495e+25
R: 1.1845e+26 C: -2.72736e+26
R: -2.56877e+26 C: -1.40334e+26
R: -1.59707e+26 C: 2.36956e+26
R: 2.13489e+26 C: 1.75858e+26
R: 1.88186e+26 C: -1.87117e+26
R: -1.58579e+26 C: -1.96216e+26
R: -1.99624e+26 C: 1.28694e+26
R: 9.83243e+25 C: 1.98238e+26
R: 1.92055e+26 C: -6.83515e+25
R: -3.96411e+25 C: -1.81234e+26
R: -1.66091e+26 C: 1.30141e+25
R: -1.07821e+25 C: 1.4709e+26
R: 1.24828e+26 C: 3.11003e+25
R: 4.74157e+25 C: -1.00009e+26
R: -7.34226e+25 C: -5.93446e+25
R: -6.66576e+25 C: 4.59154e+25
R: 1.83609e+25 C: 6.92877e+25
R: 6.73321e+25 C: 8.37101e+24
R: 3.34453e+25 C: -6.10488e+25
R: -5.08472e+25 C: -5.6091e+25
R: -7.56284e+25 C: 3.72732e+25
R: 2.09899e+25 C: 9.1493e+25
R: 1.03256e+26 C: -2.75374e+24
R: 1.66126e+25 C: -1.10637e+26
R: -1.13518e+26 C: -3.62493e+25
R: -5.52903e+25 C: 1.11943e+26
R: 1.0612e+26 C: 7.28939e+25
R: 8.82731e+25 C: -9.641e+25
R: -8.33176e+25 C: -1.00723e+26
R: -1.09648e+26 C: 6.74699e+25
R: 4.9596e+25 C: 1.14579e+26
R: 1.15195e+26 C: -3.04999e+25
R: -1.10328e+25 C: -1.11332e+26
R: -1.02987e+26 C: -7.93826e+24
R: -2.55604e+25 C: 9.03228e+25
R: 7.36601e+25 C: 4.10261e+25
R: 5.36012e+25 C: -5.34654e+25
R: -3.03357e+25 C: -6.26522e+25
R: -6.76676e+25 C: 4.97738e+24
R: -2.1819e+25 C: 6.82776e+25
R: 6.42664e+25 C: 4.92065e+25
R: 7.63116e+25 C: -5.55805e+25
R: -4.23309e+25 C: -1.02265e+26
R: -1.26233e+26 C: 2.47891e+25
R: 3.37804e+24 C: 1.47446e+26
R: 1.65227e+26 C: 2.13428e+25
R: 4.8697e+25 C: -1.79013e+26
R: -1.88379e+26 C: -7.79149e+25
R: -1.0816e+26 C: 1.93048e+26
R: 1.92905e+26 C: 1.38561e+26
R: 1.68237e+26 C: -1.88001e+26
R: -1.78547e+26 C: -1.96335e+26
R: -2.22056e+26 C: 1.64909e+26
R: 1.47599e+26 C: 2.44681e+26
R: 2.63603e+26 C: -1.2725e+26
R: -1.04597e+26 C: -2.78343e+26
R: -2.88566e+26 C: 8.04524e+25
R: 5.56738e+25 C: 2.94096e+26
R: 2.94923e+26 C: -3.1137e+25
R: -7.7029e+24 C: -2.91196e+26
R: -2.83226e+26 C: -1.38119e+25
R: -3.26645e+25 C: 2.71471e+26
R: 2.56516e+26 C: 4.82116e+25
R: 5.99321e+25 C: -2.3906e+26
R: -2.19884e+26 C: -6.74458e+25
R: -7.05266e+25 C: 1.99826e+26
R: 1.79752e+26 C: 6.91102e+25
R: 6.32966e+25 C: -1.60524e+26
R: -1.42967e+26 C: -5.33459e+25
R: -3.96696e+25 C: 1.27846e+26
R: 1.15831e+26 C: 2.28154e+25
R: 3.44753e+24 C: -1.07477e+26
R: -1.03207e+26 C: 1.76764e+25
R: 3.97327e+25 C: 1.0329e+26
R: 1.07837e+26 C: -6.18614e+25
R: -8.3196e+25 C: -1.16795e+26
R: -1.29949e+26 C: 1.02895e+26
R: 1.20172e+26 C: 1.46927e+26
R: 1.67218e+26 C: -1.34323e+26
R: -1.44753e+26 C: -1.90186e+26
R: -2.15093e+26 C: 1.50995e+26
R: 1.52729e+26 C: 2.41128e+26
R: 2.6743e+26 C: -1.49792e+26
R: -1.42185e+26 C: -2.93126e+26
R: -3.17354e+26 C: 1.30073e+26
R: 1.1378e+26 C: 3.39299e+26
R: 3.58218e+26 C: -9.37736e+25
R: -7.06559e+25 C: -3.73472e+26
R: -3.84542e+26 C: 4.51363e+25
R: 1.80094e+25 C: 3.91049e+26

Где R - действительная часть выходного массива, а C - комплекс. В чем может быть проблема? Любая помощь будет оценена.

...