MSRCR算法

MSRCR(Multi-Scale Retinex with Color Restoration)的图像增强算法

零值替换为数组中的最小非零值

def replaceZeroes(data):
    min_nonzero = min(data[np.nonzero(data)])
    data[data == 0] = min_nonzero
    return data
    # min_nonzero = min(data[np.nonzero(data)]):这行代码使用 np.nonzero() 函数找到数组 data 中所有非零元素的索引,然后使用这些索引提取非零值,并找出这些值中的最小值。

简单白平衡调整

def simple_color_balance(input_img, s1, s2):
    h, w = input_img.shape[:2]
    out_img = np.zeros([h, w])
    sort_img = input_img.copy()
    one_dim_array = sort_img.flatten()  # 转化为一维数组
    sort_array = sorted(one_dim_array)  # 对一维数组按升序排序

    per1 = int((h * w) * s1 / 100)
    minvalue = sort_array[per1]

    per2 = int((h * w) * s2 / 100)
    maxvalue = sort_array[(h * w) - 1 - per2]

    # 实施简单白平衡算法
    if (maxvalue <= minvalue):
        for i in range(h):
            for j in range(w):
                out_img[i, j] = maxvalue
    else:
        scale = 255.0 / (maxvalue - minvalue)
        for m in range(h):
            for n in range(w):
                if (input_img[m, n] < minvalue):
                    out_img[m, n] = 0
                elif (input_img[m, n] > maxvalue):
                    out_img[m, n] = 255
                else:
                    out_img[m, n] = scale * (input_img[m, n] - minvalue)  # 映射中间段的图像像素

    out_img = cv2.convertScaleAbs(out_img)
    return out_img
#函数的工作流程如下:
#1.获取输入图像的高度 h 和宽度 w。
#2.创建一个与输入图像大小相同的新图像 out_img,并将其初始化为全零。
#3.复制输入图像到 sort_img,然后将 sort_img 转换为一维数组 one_dim_array。
#4.对 one_dim_array 进行排序,得到升序排列的一维数组 sort_array。
#5.根据参数 s1 和 s2 计算两个百分比点 per1 和 per2,然后从 sort_array 中找6.到对应位置的值作为最小值 minvalue 和最大值 maxvalue。
#7.如果 maxvalue 小于等于 minvalue,则将 out_img 的所有像素设置为 maxvalue。
#8.如果 maxvalue 大于 minvalue,则计算一个缩放因子 scale,用于将输入图像的像素值映射到新的像素值范围。
#9.遍历输入图像的每个像素,如果像素值小于 minvalue,则将 out_img 对应位10.置的像素设置为 0;如果像素值大于 maxvalue,则设置为 255;否则,根据缩放因子 scale 将像素值映射到新的范围。
#11.使用 cv2.convertScaleAbs 函数对 out_img 进行转换,确保其值为整数且在 0 到 255 的范围内。

实现的是多尺度视网膜增强(Multi-Scale Retinex with Color Restoration,MSRCR)算法

def MSRCR(img, scales, s1, s2):
    if img is None:
        raise ValueError("Image is None, unable to proceed with MSRCR processing.")
    h, w = img.shape[:2]
    # print(h, w)
    scles_size = len(scales)
    img = np.array(img, dtype=np.float64)
    # print(img)
    log_R = np.zeros((h, w), dtype=np.float64)
    img_sum = np.add(img[:, :, 0], img[:, :, 1], img[:, :, 2])
    img_sum = replaceZeroes(img_sum)
    gray_img = []

    for j in range(3):
        img[:, :, j] = replaceZeroes(img[:, :, j])
        for i in range(0, scles_size):
            L_blur = cv2.GaussianBlur(img[:, :, j], (scales[i], scales[i]), 0)
            L_blur = replaceZeroes(L_blur)

            dst_img = cv2.log(img[:, :, j])
            dst_Lblur = cv2.log(L_blur)
            log_R += cv2.subtract(dst_img, dst_Lblur)
        MSR = log_R / 3.0
        '''
            img_sum_log = np.zeros((h, w))
            for i in range(0, h):
                for k in range(0, w):
                    img_sum_log[i,k] = 125.0*math.log(img[i,k,j]) - math.log(img_sum[i,k])
            MSRCR = MSR * (img_sum_log[:, :])
            print(img_sum)
            # x = cv2.log(img_sum)
            '''
        MSRCR = MSR * (cv2.log(125.0 * img[:, :, j]) - cv2.log(img_sum))
        gray = simple_color_balance(MSRCR, s1, s2)
        gray_img.append(gray)

    return gray_img

主函数

if __name__ == '__main__':
    scales = [15, 101, 301]
    s1, s2 = 2, 3
    src_img = cv2.imread('sc.jpg')
    # 设置窗口大小
    cv2.namedWindow('Original Image', cv2.WINDOW_NORMAL)
    cv2.namedWindow('Enhanced(MSRCR) Image', cv2.WINDOW_NORMAL)
    cv2.resizeWindow('Original Image', 600, 400)  # 设置'Original Image'窗口大小为600x400
    cv2.resizeWindow('Enhanced(MSRCR) Image', 600, 400)  # 设置'Enhanced(MSRCR) Image'窗口大小为600x400

    cv2.imshow('Original Image', src_img)
    MSRCR_Out = MSRCR(src_img, scales, s1, s2)

    result = cv2.merge([MSRCR_Out[0], MSRCR_Out[1], MSRCR_Out[2]])

    cv2.imshow('Enhanced(MSRCR) Image', result)
    cv2.waitKey(0)
    cv2.destroyAllWindows()

总代码

import cv2
import numpy as np
import math


def replaceZeroes(data):
    min_nonzero = min(data[np.nonzero(data)])
    data[data == 0] = min_nonzero
    return data


def simple_color_balance(input_img, s1, s2):
    h, w = input_img.shape[:2]
    out_img = np.zeros([h, w])
    sort_img = input_img.copy()
    one_dim_array = sort_img.flatten()  # 转化为一维数组
    sort_array = sorted(one_dim_array)  # 对一维数组按升序排序

    per1 = int((h * w) * s1 / 100)
    minvalue = sort_array[per1]

    per2 = int((h * w) * s2 / 100)
    maxvalue = sort_array[(h * w) - 1 - per2]

    # 实施简单白平衡算法
    if (maxvalue <= minvalue):
        for i in range(h):
            for j in range(w):
                out_img[i, j] = maxvalue
    else:
        scale = 255.0 / (maxvalue - minvalue)
        for m in range(h):
            for n in range(w):
                if (input_img[m, n] < minvalue):
                    out_img[m, n] = 0
                elif (input_img[m, n] > maxvalue):
                    out_img[m, n] = 255
                else:
                    out_img[m, n] = scale * (input_img[m, n] - minvalue)  # 映射中间段的图像像素

    out_img = cv2.convertScaleAbs(out_img)
    return out_img


def MSRCR(img, scales, s1, s2):
    if img is None:
        raise ValueError("Image is None, unable to proceed with MSRCR processing.")
    h, w = img.shape[:2]
    # print(h, w)
    scles_size = len(scales)
    img = np.array(img, dtype=np.float64)
    # print(img)
    log_R = np.zeros((h, w), dtype=np.float64)
    img_sum = np.add(img[:, :, 0], img[:, :, 1], img[:, :, 2])
    img_sum = replaceZeroes(img_sum)
    gray_img = []

    for j in range(3):
        img[:, :, j] = replaceZeroes(img[:, :, j])
        for i in range(0, scles_size):
            L_blur = cv2.GaussianBlur(img[:, :, j], (scales[i], scales[i]), 0)
            L_blur = replaceZeroes(L_blur)

            dst_img = cv2.log(img[:, :, j])
            dst_Lblur = cv2.log(L_blur)
            log_R += cv2.subtract(dst_img, dst_Lblur)
        MSR = log_R / 3.0
        '''
            img_sum_log = np.zeros((h, w))
            for i in range(0, h):
                for k in range(0, w):
                    img_sum_log[i,k] = 125.0*math.log(img[i,k,j]) - math.log(img_sum[i,k])
            MSRCR = MSR * (img_sum_log[:, :])
            print(img_sum)
            # x = cv2.log(img_sum)
            '''
        MSRCR = MSR * (cv2.log(125.0 * img[:, :, j]) - cv2.log(img_sum))
        gray = simple_color_balance(MSRCR, s1, s2)
        gray_img.append(gray)

    return gray_img


if __name__ == '__main__':
    scales = [15, 101, 301]
    s1, s2 = 2, 3
    src_img = cv2.imread('sc.jpg')
    # 设置窗口大小
    cv2.namedWindow('Original Image', cv2.WINDOW_NORMAL)
    cv2.namedWindow('Enhanced(MSRCR) Image', cv2.WINDOW_NORMAL)
    cv2.resizeWindow('Original Image', 600, 400)  # 设置'Original Image'窗口大小为600x400
    cv2.resizeWindow('Enhanced(MSRCR) Image', 600, 400)  # 设置'Enhanced(MSRCR) Image'窗口大小为600x400

    cv2.imshow('Original Image', src_img)
    MSRCR_Out = MSRCR(src_img, scales, s1, s2)

    result = cv2.merge([MSRCR_Out[0], MSRCR_Out[1], MSRCR_Out[2]])

    cv2.imshow('Enhanced(MSRCR) Image', result)
    cv2.waitKey(0)
    cv2.destroyAllWindows()

增强前:
在这里插入图片描述
增强后:
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值