Histoformer / Allweather /compute_psnr.py
sunshangquan
commit from ssq
111d9b6
import argparse
import cv2
import os
import numpy as np
from skimage.metrics import mean_squared_error
from skimage.measure import compare_ssim
from skimage.metrics import structural_similarity
from skimage.metrics import peak_signal_noise_ratio
#import lpips
import torch
from tqdm import tqdm
#from niqe.niqe import compute_niqe
#criterion = lpips.LPIPS(net='vgg', lpips=True, pnet_rand=False, pretrained=True).cuda()
def rgb2ycbcr(im, only_y=True):
'''
same as matlab rgb2ycbcr
:parame img: uint8 or float ndarray
'''
in_im_type = im.dtype
im = im.astype(np.float64)
if in_im_type != np.uint8:
im *= 255.
# convert
if only_y:
rlt = np.dot(im, np.array([65.481, 128.553, 24.966])/ 255.0) + 16.0
else:
rlt = np.matmul(im, np.array([[65.481, -37.797, 112.0 ],
[128.553, -74.203, -93.786],
[24.966, 112.0, -18.214]])/255.0) + [16, 128, 128]
if in_im_type == np.uint8:
rlt = rlt.round()
else:
rlt /= 255.
return rlt.astype(in_im_type)
def rgb2ycbcrTorch(im, only_y=True):
'''
same as matlab rgb2ycbcr
Input:
im: float [0,1], N x 3 x H x W
only_y: only return Y channel
'''
im_temp = im.permute([0,2,3,1]) * 255.0 # N x H x W x C --> N x H x W x C, [0,255]
# convert
if only_y:
rlt = torch.matmul(im_temp, torch.tensor([65.481, 128.553, 24.966],
device=im.device, dtype=im.dtype).view([3,1])/ 255.0) + 16.0
else:
rlt = torch.matmul(im_temp, torch.tensor([[65.481, -37.797, 112.0 ],
[128.553, -74.203, -93.786],
[24.966, 112.0, -18.214]],
device=im.device, dtype=im.dtype)/255.0) + \
torch.tensor([16, 128, 128]).view([-1, 1, 1, 3])
rlt /= 255.0
rlt.clamp_(0.0, 1.0)
return rlt.permute([0, 3, 1, 2])
def readim(file):
# print(file)
img = cv2.imread(file)
img = img.astype(np.float32)
return img / 255.
def loadfiles(folder):
files = os.listdir(folder)
return natsorted(files)
def resize(im, size, crop=True):
if crop:
return im[:size[0], :size[1]]
else:
return cv2.resize(im, size)
from natsort import natsorted
def np2torch(img):
im = img.astype(np.float32) / 255
im = torch.tensor(im).permute((2,0,1)).unsqueeze(0)
return im.cuda()
def compute_metrics(path1, path2, ycbcr=True):
print(path1)
files1 = loadfiles(path1)
files2 = loadfiles(path2)
print(len(files1), len(files2))
psnr = []
ssim = []
mse = []
lpips = []
niqe = []
crop = False
for file1, file2 in tqdm(zip(files1, files2)):
img1 = readim(os.path.join(path1, file1))
img2 = readim(os.path.join(path2, file2))
if img1.shape != img2.shape:
if not crop:
img1 = resize(img1, img2.shape[:2][::-1], False)
else:
img1 = resize(img1, img2.shape, True)
# print(img1.shape, img2.shape, img1.max())
MSE = mean_squared_error(img1, img2)
if ycbcr:
img1 = rgb2ycbcr(img1, True)
img2 = rgb2ycbcr(img2, True)
diff = (img2 - img1)
# print(diff.mean(), diff.max(), diff.min(), diff.shape)
PSNR = peak_signal_noise_ratio(img1, img2, data_range=1)
SSIM = structural_similarity(img1, img2, win_size=11, multichannel=False if ycbcr else True, data_range=1)
mse.append(MSE)
psnr.append(PSNR)
ssim.append(SSIM)
mean_mse, mean_psnr, mean_ssim = np.mean(mse), np.mean(psnr), np.mean(ssim)
print(mean_mse, mean_psnr, mean_ssim)
return mean_mse, mean_psnr, mean_ssim
if __name__ == "__main__":
parser = argparse.ArgumentParser()
# path setting
parser.add_argument('--path1', type=str,default= "") # modify the experiments name-->modify all save path
parser.add_argument('--path2', type=str,default= "")
args = parser.parse_args()
path1 = ''
path2 = ''
if len(args.path1) != 0:
path1 = args.path1
if len(args.path2) != 0:
path2 = args.path2
compute_metrics(path1, path2, True)