基于OpenCV的图形分析辨认03

news2025/1/16 18:57:55

目录

一、前言

二、实验目的

三、实验内容

四、实验过程


一、前言

编程语言:Python,编程软件:vscode或pycharm,必备的第三方库:OpenCV,numpy,matplotlib,os等等。

关于OpenCV,numpy,matplotlib,os等第三方库的下载方式如下:

第一步,按住【Windows】和【R】调出运行界面,输入【cmd】,回车打开命令行。

第二步,输入以下安装命令(可以先升级一下pip指令)。

pip升级指令:

python -m pip install --upgrade pip

 opencv库的清华源下载:

pip install opencv-python  -i https://pypi.tuna.tsinghua.edu.cn/simple

numpy库的清华源下载:

 pip install numpy  -i https://pypi.tuna.tsinghua.edu.cn/simple

matplotlib库的清华源下载:

pip install matplotlib -i https://pypi.tuna.tsinghua.edu.cn/simple

os库的清华源下载:

pip install os  -i https://pypi.tuna.tsinghua.edu.cn/simple 

二、实验目的

1.了解不同图像亮度变换算法;

2.基于演算法原理,以函数形式实现图像亮度变换;

3.根据实验内容2-4要求,调试出所提供图片对应的参数;

三、实验内容

1.任选一张彩色图完成课堂教授内容,并以函数形式封装功能,包含:

  1. Image Negatives
  2. Log Transformations
  3. Power-Law Transformations
  4. Piecewise-Linear Transformations
  5. Contrast Stretching
  6. Gray-Level Slicing
  7. Bit-Plane Slicing

2.透过gramma correction,尝试不同参数,将下图還原成原亮度。

3.透过gramma correction,尝试不同参数,将下图還原成原亮度。

4.透过Bit-Plane Slicing,尝试获得下图结果。

Hint:考虑移除细节部分

四、实验过程

根据原理写成一个代码文件,命名为【Methods】,具体代码如下:

import cv2
import numpy as np

def Image_Negatives(img):
    # 将输入图像转换为灰度图像和反转图像的函数
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    dst = 255 - gray
    return dst

def Log(img, c):
    # 对输入图像进行对数运算并缩放
    output = c * np.log(1.0 + img)
    output = np.uint8(output + 0.5)
    return output

def Gamma(img, k):
    # 对图像进行伽马校正
    img_gamma = np.power(img, k)  # 将图像的每个像素值的幂次方为k
    normImg = 255. * (img_gamma - img_gamma.min()) / (img_gamma.max() - img_gamma.min() + 1e-6)  # 对归一化后的图像进行重新线性化
    img_Gamma = np.uint8(normImg)  # 将归一化后的图像转换为0到255之间的无符号整型
    return img_Gamma  # 返回伽马校正后的图像

def Contrast_Stretching(img, height, width):
    rMin = img.min()  # 查找图像最低像素值
    rMax = img.max()  # 查找图像最高像素值
    r1, s1 = rMin, 0  # 初始化r1和s1为最低像素值和0
    r2, s2 = rMax, 255  # 初始化r2和s2为最高像素值和255
    img_Stretch = np.empty((width, height), np.uint8)  # 创建一个与输入图像相同大小的空矩阵,用于存储扩展对比度后的图像
    k1 = s1 / r1  # 计算k1,用于将低于最低像素值的像素值映射到0
    k2 = (s2 - s1) / (r2 - r1)  # 计算k2,用于将介于最低像素值和最高像素值之间的像素值映射到0到255的范围
    k3 = (255 - s2) / (255 - r2)  # 计算k3,用于将高于最高像素值的像素值映射到0到255的范围
    for h in range(height):  # 遍历图像的每一行
        for w in range(width):  # 遍历图像的每一列
            if img[h, w] < r1:  # 如果像素值低于最低像素值
                img_Stretch[h, w] = k1 * img[h, w]  # 将像素值映射到0
            elif r1 <= img[h, w] <= r2:  # 如果像素值介于最低像素值和最高像素值之间
                img_Stretch[h, w] = k2 * (img[h, w] - r1) + s1  # 将像素值映射到0到255的范围
            elif img[h, w] > r2:  # 如果像素值高于最高像素值
                img_Stretch[h, w] = k3 * (img[h, w] - r2) + s2  # 将像素值映射到0到255的范围
    return img_Stretch  # 返回扩展对比度后的图像

def Gray_Level_Slicing(img, a, b, form):
    img1 = img.copy()  # 复制图像矩阵
    if form == "binary":  # 如果形式为二值化
        img1[(img1[:, :] < a) | (img1[:, :] > b)] = 0  # 将灰度值小于a或大于b的像素点设置为0
        img1[(img1[:, :] >= a) & (img1[:, :] <= b)] = 255  # 将灰度值大于等于a且小于等于b的像素点设置为255
    elif form == "grayscale":  # 如果形式为灰度化
        img1[(img1[:, :] >= a) & (img1[:, :] <= b)] = 255  # 将灰度值大于等于a且小于等于b的像素点设置为255
    return img1  # 返回处理后的图像矩阵

def Bit_Plane_Slicing(img, height, width, i):
    # 将图像的每个像素点转换为8位二进制表示,然后提取第i个比特位,生成一个新的图像。
    imgBit = np.empty((height, width), dtype = np.uint8)
    for h in range(height):
        for w in range(width):
            x = np.binary_repr(img[h, w], width = 8)
            x = x[::-1]
            a = x[i - 1]
            imgBit[h, w] = int(a)
    return imgBit

利用上述原理代码实现各种图片变化,执行代码如下:

import cv2
import numpy as np
import matplotlib.pyplot as plt
from Methods import *

def image_negatives():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\img1.jpg")
    img_gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    # 调用Image_Negatives函数对图像进行反转处理
    img_negative = Image_Negatives(img)
    # 绘制原始图像、灰度图像、反转图像
    plt.subplot(1, 3, 1), plt.imshow(cv2.cvtColor(img, cv2.COLOR_BGR2RGB)), plt.title('Original img'), plt.axis('off')
    plt.subplot(1, 3, 2), plt.imshow(img_gray, cmap = 'gray'), plt.title('gray img'), plt.axis('off')
    plt.subplot(1, 3, 3), plt.imshow(img_negative, cmap = 'gray'), plt.title('dst img'), plt.axis('off')
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def log():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\img1.jpg", 0)
    # 调用Log函数对图像进行对数变换
    output = Log(img, 40)
    # 绘制原始图像、对数变换图像
    plt.subplot(1, 2, 1), plt.imshow(img, cmap = 'gray', vmin = 0, vmax = 225), plt.title('Original img'), plt.axis('off')
    plt.subplot(1, 2, 2), plt.imshow(output,cmap = 'gray', vmin = 0, vmax = 225), plt.title('output img'), plt.axis('off')
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def gamma():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\img1.jpg", 0)
    # 定义Gamma值列表
    gammaList = [0.125, 0.25, 0.5, 1.0, 2.0, 4.0]
    
    for k in range(len(gammaList)):
        # 调用Gamma函数对图像进行Gamma校正
        imgGamma = Gamma(img, gammaList[k])
        # 设置子图参数,关闭坐标轴
        plt.subplot(2, 3, k + 1), plt.axis('off')
        # 显示图像,设置灰度映射范围
        plt.imshow(imgGamma, cmap = 'gray', vmin = 0, vmax = 255)
        # 设置子图标题,插入Gamma值
        plt.title(f"$\gamma = {gammaList[k]}$")
    
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def contrast_stretching():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\img1.jpg", 0)
    # 获取图像的高度和宽度
    height, width = img.shape[:2]
    # 进行对比度拉伸
    img_stretch = Contrast_Stretching(img, height, width)
    # 显示原始图像、拉伸图像
    plt.subplot(1, 2, 1), plt.imshow(img, cmap = 'gray', vmin = 0, vmax = 255), plt.title('Original img'), plt.axis("off")
    plt.subplot(1, 2, 2), plt.imshow(img_stretch, cmap = 'gray', vmin = 0, vmax = 255), plt.title('Stretch img'), plt.axis("off")
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def gray_level():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\img1.jpg", 0)
    # 设置阈值范围
    a, b = 155, 245
    # 生成二值图像
    form = "binary"
    # 使用灰度切割法生成二值图像
    img_binary = Gray_Level_Slicing(img, a, b, form)
    # 生成灰度图像
    form = "grayscale"
    # 使用灰度切割法生成灰度图像
    img_grayscale = Gray_Level_Slicing(img, a, b, form)
    # 显示原始图像、二值图像和灰度图像
    plt.subplot(1, 3, 1), plt.imshow(img, cmap = 'gray'), plt.title('Original img'), plt.axis('off')
    plt.subplot(1, 3, 2), plt.imshow(img_binary, cmap = 'gray'), plt.title('Binary img'), plt.axis('off')
    plt.subplot(1, 3, 3), plt.imshow(img_grayscale, cmap = 'gray'), plt.title('Grayscale img'), plt.axis('off')
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def bit_plane():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\img1.jpg", 0)
    height, width = img.shape[:2]
    
    for i in range(9, 0, -1):
        # 创建子图并设置子图位置和刻度
        plt.subplot(3, 3, (9 - i) + 1, xticks = [], yticks = [])
        if i == 9:
            # 显示原始图像并添加标题
            plt.imshow(img, cmap = 'gray'), plt.title('Original img')
        else:
            # 进行位平面切割并显示切割后的图像,添加标题
            img_bit = Bit_Plane_Slicing(img, height, width, i)
            plt.imshow(img_bit, cmap = 'gray'), plt.title(f"{bin((i - 1))}")
    
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

# 执行相应函数
image_negatives()
log()
gamma()
contrast_stretching()
gray_level()
bit_plane()

接下来是每种方法对图像的变化情况,具体演示如下:

1.(1)图像反转:

(2)对数变换:

 

(3)伽马变换:

(4)对比度拉伸:

(5)灰度级分层:

(6)比特平面分层:

2.问题二到四的还原亮度代码如下:

import cv2
import numpy as np
import matplotlib.pyplot as plt
from Methods import *

def question1():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\HW3-2.jpg", 0)
    # 定义Gamma值列表
    gammaList = [0.025, 0.05, 0.075, 0.1, 0.125, 0.15, 0.175, 0.2, 0.225, 0.25, 0.275, 0.3, 0.325, 0.35, 0.375, 0.4]

    for k in range(len(gammaList)):
        # 调用Gamma函数对图像进行Gamma校正
        imgGamma = Gamma(img, gammaList[k])
        # 设置子图参数,关闭坐标轴
        plt.subplot(4, 4, k + 1), plt.axis('off')
        # 显示图像,设置灰度映射范围
        plt.imshow(imgGamma, cmap = 'gray', vmin = 0, vmax = 255)
        # 设置子图标题,插入Gamma值
        plt.title(f"$\gamma = {gammaList[k]}$")
    
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def question2():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\HW3-3.jpg", 0)
    # 定义Gamma值列表
    gammaList = [1.0, 1.1, 1.2, 1.3, 1.4, 1.5, 1.6, 1.7, 1.8, 1.9, 2.0, 2.1, 2.2, 2.3, 2.4, 2.5]
    
    for k in range(len(gammaList)):
        # 调用Gamma函数对图像进行Gamma校正
        imgGamma = Gamma(img, gammaList[k])
        # 设置子图参数,关闭坐标轴
        plt.subplot(4, 4, k + 1), plt.axis('off')
        # 显示图像,设置灰度映射范围
        plt.imshow(imgGamma, cmap = 'gray', vmin = 0, vmax = 255)
        # 设置子图标题,插入Gamma值
        plt.title(f"$\gamma = {gammaList[k]}$")
    
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

def question3():
    # 读取图像并转换为灰度图像
    img = cv2.imread(r"D:\Image\HW3-4.jpg", 0)
    height, width = img.shape[:2]
    
    for i in range(9, 0, -1):
        # 创建子图并设置子图位置和刻度
        plt.subplot(3, 3, (9 - i) + 1, xticks = [], yticks = [])
        if i == 9:
            # 显示原始图像并添加标题
            plt.imshow(img, cmap = 'gray'), plt.title('Original img')
        else:
            # 进行位平面切割并显示切割后的图像,添加标题
            img_bit = Bit_Plane_Slicing(img, height, width, i)
            plt.imshow(img_bit, cmap = 'gray'), plt.title(f"{bin((i - 1))}")
    
    # 调整图像布局并显示图像
    plt.tight_layout()
    plt.show()

# 执行相应函数解决相应问题
question1()
question2()
question3()

对于问题二,代码运行效果如下:

伽马变换的伽马值为0.1到0.3之间较为合适,与题目要求图像最为接近。

3.问题三的代码运行效果如下:

伽马变换的伽马值为1.0到2.0之间较为合适,与题目要求图像最为接近。

4.问题四的代码运行效果如下:

从实验结果来看,比特平面分层中的第八层和第七层较为符合题目图像。

都看到最后了,不点个赞吗?

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1496743.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

利用MATLAB模拟点电荷的电场分布

一、实验目的&#xff1a; 1&#xff0e;熟悉点电荷的电场分布情况&#xff1b; 2&#xff0e;学会使用Matlab绘图&#xff1b; 二、实验内容&#xff1a; 1&#xff0e;根据库伦定律&#xff0c;利用Matlab强大的绘图功能画出单个点电荷的电场分布情况&#xff0c;包括电力…

基于SpringBoot+Vue 的专家医院预约挂号系统

博主介绍&#xff1a;✌程序员徐师兄、7年大厂程序员经历。全网粉丝12w、csdn博客专家、掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域和毕业项目实战✌ &#x1f345;文末获取源码联系&#x1f345; &#x1f447;&#x1f3fb; 精彩专栏推荐订阅&#x1f447;…

Type-C接口小家电使用PD诱骗芯片获取充电器的5V9V12V20V供电

随着Type-C接口的逐渐普及&#xff0c;小家电设备慢慢开始采用Type-C&#xff0c;淘汰了以往的DC接口&#xff0c;Type-C接口在小家电设备中的应用也越来越广泛。Type-C接口支持大电流宽电压范围&#xff0c;如何确保设备能够正确识别并使用各种电压&#xff08;例如5V、9V、12…

Go编程实战:高效利用encoding/binary进行数据编解码

Go编程实战&#xff1a;高效利用encoding/binary进行数据编解码 引言encoding/binary 包核心概念ByteOrder 接口Binary 数据类型的处理处理复杂数据结构 基础使用教程数据类型与二进制格式的映射基本读写操作写操作 - binary.Write读操作 - binary.Read 错误处理 高级功能与技巧…

可调恒定电流稳压器NSI50150ADT4G车规级LED驱动器 提供专业的汽车级照明解决方案

NSI50150ADT4G产品概述&#xff1a; NSI50150ADT4G可调恒定电流稳压器 (CCR) &#xff0c;是一款简单、经济和耐用的器件&#xff0c;适用于为 LED 中的调节电流提供成本高效的方案&#xff08;与恒定电流二极管 CCD 类似&#xff09;。该 (CCR) 基于自偏置晶体管 (SBT) 技术&…

Java开发从入门到精通(一):Java的基础语法进阶

Java大数据开发和安全开发 &#xff08;一&#xff09;Java注释符1.1 单行注释 //1.2 多行注释 /* */1.3 文档注释 /** */1.4 各种注释区别1.5 注释的特点1.5 注释的快捷键 &#xff08;二&#xff09;Java的字面量&#xff08;三&#xff09;Java的变量3.1 认识变量3.2 为什么…

使用SMTP javamail发送邮件

一、SMTP协议 SMTP(Simple Mail Transfer Protocol)即简单邮件传输协议,它是一组用于由源地址到目的地址传送邮件的规则&#xff0c;由它来控制信件的中转方式。SMTP协议属于TCP/IP协议簇&#xff0c;它帮助每台计算机在发送或中转信件时找到下一个目的地。使用javamail编写发送…

【JavaEE】_Spring MVC 项目单个及多个参数传参

目录 1. 传递单个参数 1.1 关于参数名的问题 2. 传递多个参数 2.1 关于参数顺序的问题 2.2 关于基本类型与包装类的问题 1. 传递单个参数 现创建Spring MVC项目&#xff0c;.java文件内容如下&#xff1a; package com.example.demo.controller;import org.springframewo…

NCDA 大赛 App 设计获奖作品分享!

未来设计师全国高校数字艺术设计大赛简称“NCDA大赛”&#xff0c;是由工信部人才交流中心主办&#xff0c;直接对联合国接国际设计赛事的一个大学生竞赛&#xff0c;不仅由教育部中国高等教育学会认定&#xff0c;教育厅发文立项&#xff0c;还有来自我们都很熟悉的“学习强国…

vue3中指定组件名称:可以使用插件vite-plugin-vue-setup-extend

第一步&#xff1a;安装vite-plugin-vue-setup-extend插件 第二步&#xff1a;修改vite.config.ts文件配置

C#多线程(4)——任务并行库TPL

文章目录 1 什么是TPL2 创建与启动任务3 等待任务4 任务中的异常处理5 取消任务 1 什么是TPL T P L \textcolor{red}{TPL} TPL&#xff08;Task Parallel Library&#xff09;任务并行库&#xff0c;是从.NetFramwork4.0后引入的基于异步操作的一组API。TPL的底层是基于多线程实…

nginx: mac使用vscode本地调试nginx

vscode安装c语言插件 在extensions中搜索"c/c"&#xff0c; 将前3个插件都安装 在extensions中搜索"cmake"&#xff0c; 将前2个插件都安装 下载nginx源码 nginx 源码: https://github.com/nginx/nginx 编译运行Nginx 修改 /auto/cc/conf 文件&…

【论文阅读】单词级文本攻击TAAD2.2

TAAD2.2论文概览 0.前言1-101.Bridge the Gap Between CV and NLP! A Gradient-based Textual Adversarial Attack Frameworka. 背景b. 方法c. 结果d. 论文及代码 2.TextHacker: Learning based Hybrid Local Search Algorithm for Text Hard-label Adversarial Attacka. 背景b…

数据结构——lesson6二叉树基础

前言 hellohello~这里是土土数据结构学习笔记&#x1f973;&#x1f973; &#x1f4a5;个人主页&#xff1a;大耳朵土土垚的博客 &#x1f4a5; 所属专栏&#xff1a;数据结构学习笔记 &#x1f4a5;对于数据结构顺序表链表有疑问的都可以在上面数据结构的专栏进行学习哦~感…

ping多个IP的工具

Ping Tool 项目地址 python开发的IP搜索小工具 ping一个网段所有IP&#xff0c;显示结果查看某个ip地址开放监听的端口配置可保存

查询IP地址保障电商平台安全

随着电子商务的快速发展&#xff0c;网购已经成为人们日常生活中不可或缺的一部分。然而&#xff0c;网络交易安全一直是人们关注的焦点之一&#xff0c;尤其是在面对日益频发的网络诈骗和欺诈行为时。为了提高网购平台交易的安全性&#xff0c;一种有效的方法是通过查询IP地址…

Java红黑树实现Map简单示例

红黑树&#xff08;Red-Black Tree&#xff09;是一种自平衡的二叉搜索树&#xff0c;它是由 Rudolf Bayer 在 1972 年提出的&#xff0c;后来由 Leo J. Guibas 和 Robert Sedgewick 在 1978 年发表的论文中形式化定义。 红黑树具有以下特性&#xff1a; 1.节点颜色&#xff1…

java数据结构与算法刷题-----LeetCode653. 两数之和 IV - 输入二叉搜索树

java数据结构与算法刷题目录&#xff08;剑指Offer、LeetCode、ACM&#xff09;-----主目录-----持续更新(进不去说明我没写完)&#xff1a;https://blog.csdn.net/grd_java/article/details/123063846 文章目录 1. 前序遍历加hash2. 中序遍历双指针 1. 前序遍历加hash 解题思…

(上海电力展)2024上海国际智慧电力与电气设备展览会

2024上海国际智慧电力与电气设备展览会 2024 Shanghai International Intelligent Power and Electrical Equipment Exhibition 时 间&#xff1a;2024年7月13-15日 地 点&#xff1a;上海新国际博览中心 展会简介Introduction 随着全球进入互联网和数字经济时…

逻辑分析仪分析硬件spi

一&#xff0c;cubemx配置好后&#xff0c;使用spi接口发送数据&#xff1b; 发送5个字节&#xff1a;1&#xff0c;2&#xff0c;3&#xff0c;4&#xff0c;5&#xff1b; 第1个字节&#xff1a;1&#xff1b; 第2个字节&#xff1a;2&#xff1b; 第3个字节&#xff1a;3&am…