본문 바로가기
Computer Science/영상처리

(C/C++) Quality Evaluation(PSNR)

by BaekDaBang 2024. 3. 27.

1. Subjective Quality

 

2. Objective Quality

이미지 퀄리티에 대한 객관적인 측정 지표 필요

 

Peak Signal-to-Noise Ratio, PSNR

$MSE = \frac{\sum_{j=1, i=1}^{j=h, i=w}(Original - Output)^2}{h \times w} $

$MAX = 2^{bit - depth} - 1$

$PSNR = 10\cdot log_{10} \left ( \frac{MAX^2}{MSE} \right ) $

double mse = 0, psnr;

for(int j=0; j<height; j++)
{
    {
        mse += (double)((Y2[j * width + i] - Y1[j * width + i]) * (Y2[j * width + i] - Y1[j * width * i]));
    }
}

mse /= (width * height);
psnr = mse != 0.0 ? 10.0 * log10(255 * 255 / mse) : 99.99;
printf("MSE = %.2lf\nPSNR = %.2lf dB\n", mse, psnr);

 

3. Implementation

#define _CRT_SECURE_NO_WARNINGS
#include <stdio.h>
#include <stdlib.h>
#include <windows.h>
#include <math.h>

int main(int argc, char* argv[]) {

    BITMAPFILEHEADER bmpFile;
    BITMAPINFOHEADER bmpInfo;
    FILE* inputFile1 = NULL, * inputFile2 = NULL;
    inputFile1 = fopen("AICenterY.bmp", "rb");          //AICenter 사진
    inputFile2 = fopen("AICenterY_Noise.bmp", "rb");    //AICenterY_Noise 사진

    fread(&bmpFile, sizeof(BITMAPFILEHEADER), 1, inputFile1);
    fread(&bmpInfo, sizeof(BITMAPINFOHEADER), 1, inputFile1);

    fread(&bmpFile, sizeof(BITMAPFILEHEADER), 1, inputFile2);
    fread(&bmpInfo, sizeof(BITMAPINFOHEADER), 1, inputFile2);

    int width = bmpInfo.biWidth;
    int height = bmpInfo.biHeight;
    int size = bmpInfo.biSizeImage;
    int bitCnt = bmpInfo.biBitCount;
    int stride = (((bitCnt / 8) * width) + 3) / 4 * 4;
    //printf("W: %d(%d)\nH: %d\nS: %d\nD: %d\n\n", width, stride, height, size, bitCnt);

    unsigned char* inputImg1 = NULL, * inputImg2 = NULL;
    inputImg1 = (unsigned char*)calloc(size, sizeof(unsigned char));
    inputImg2 = (unsigned char*)calloc(size, sizeof(unsigned char));
    fread(inputImg1, sizeof(unsigned char), size, inputFile1);
    fread(inputImg2, sizeof(unsigned char), size, inputFile2);

    unsigned char* Y1 = (unsigned char*)calloc(width * height, sizeof(unsigned char));   //원본 정보 저장
    unsigned char* Y2 = (unsigned char*)calloc(width * height, sizeof(unsigned char));   //노이즈 발생한 사진 정보 저장
    

    for (int j = 0; j < height; j++) {
        for (int i = 0; i < width; i++) {
            Y1[j * width + i] = inputImg1[j * stride + 3 * i + 0];
            Y2[j * width + i] = inputImg2[j * stride + 3 * i + 0];
        }
    }

    double mse = 0, psnr;

    for (int j = 0; j < height; j++) {
        for (int i = 0; i < width; i++) {
            mse += (double)((Y2[j * width + i] - Y1[j * width + i]) * (Y2[j * width + i] - Y1[j * width + i]));
        }
    }

    mse /= (width * height);
    psnr = mse != 0.0 ? 10.0 * log10(255 * 255 / mse) : 99.99;
    printf("MSE = %.2lf\nPSNR = %.2lf dB\n", mse, psnr);
 
    
    free(inputImg1);
    free(inputImg2);
    fclose(inputFile1);
    fclose(inputFile2);

    return 0;
}

'Computer Science > 영상처리' 카테고리의 다른 글

(C/C++) Histogram  (0) 2024.04.02
(C/C++) Filter (Denoising)  (0) 2024.04.01
(C/C++) Pixel Operation  (0) 2024.03.27
(C/C++) Color Model  (0) 2024.03.27
(C/C++) Image Format  (0) 2024.03.27