图像处理:手写实现图像增广算法(旋转、亮度调整、裁剪与拼接)

news2024/11/28 0:40:45

前言

图像增广算法在计算机视觉领域扮演着至关重要的角色。随着深度学习的兴起,大规模数据集的需求变得更加迫切,而图像增广算法可以通过对原始图像进行一系列变换,扩充数据集,从而提升模型的泛化能力和鲁棒性。

本文将着重介绍图像增广算法中的三个关键方面:图像旋转、图像亮度调整以及图像裁剪与拼接。这些算法不仅能够增加训练数据的多样性,还可以帮助我们解决一些实际问题,例如旋转不变性、光照变化以及物体完整性等。

而采用了随机参数的图像增广算法可以增加数据多样性、减少过拟合、增强模型的鲁棒性,并扩充数据集规模,从而改善模型的性能和泛化能力。

基础实现

我们需要先了解一下图像增广算法的基础实现是怎么样的。

这里我们将使用一些Python优秀的第三方库来完成。在图像增广方面,有许多可供选择的第三方库,如PIL/Pillow、OpenCV、scikit-image等。而在PyTorch中也提供了一些图像增广的函数,虽然图像增广算法在PyTorch中也属于预处理的一部分,但为了方便起见,我们仍然选择使用大家较为熟悉的OpenCV库,而不使用PyTorch。

a.旋转

def Rotated_image(img, angle = 45, scale = 1.0):
    height, width = img.shape[:2]
    center = (width // 2, height // 2)
    matrix = cv2.getRotationMatrix2D(center, angle, scale) #旋转中心,旋转角度,缩放比例
    rotated_image = cv2.warpAffine(img, matrix, (width, height))
    return rotated_image

通过cv2.getRotationMatrix2D函数计算旋转矩阵,然后使用cv2.warpAffine函数执行旋转操作。最后,使用cv2.imshow函数显示旋转前后的图像。 

实验结果: 

原始图片与旋转图片

b.亮度调整

def Adjusted_image(img,brightness_factor = 1.5):
    image_float = img.astype(np.float32)
    adjusted_image = image_float * brightness_factor
    # 将图像像素值限制在[0, 255]范围内
    adjusted_image = np.clip(adjusted_image, 0, 255)
    adjusted_image = adjusted_image.astype(np.uint8)
    return adjusted_image

将图像转换为浮点型数据类型。然后,通过乘以一个亮度调整因子来调整图像的亮度,这里的亮度调整因子可以根据具体需求进行调整。接下来,我们使用np.clip函数将图像像素值限制在[0, 255]范围内,避免溢出。最后,我们将图像转换回无符号8位整数类型,并显示调整后的图像。

实验结果:

原始图片与亮度调整图片

c.裁剪及拼接

裁剪

def Cut_image(image, coordinate, Leath, cropImg=False ,save=False, saveFile=''):
    imageH,imageW=image.shape[:2]
    x, y = coordinate[0], coordinate[1]
    width, height = Leath[0], Leath[1]
    h, w = height, width
    if x < 0:
        x = 0
    if y < 0:
        y = 0
    if x + width > imageW:
        width = imageW - x
    if y + height > imageH:
        height = imageH - y

    cropped_image = image[y:y + height, x:x + width]
    padded_image = np.full((h, w, 3), 128, dtype=np.uint8)
    x_offset = (w - width) // 2
    y_offset = (h - height) // 2
    padded_image[y_offset:y_offset + height, x_offset:x_offset + width] = cropped_image
    if save:
        cv2.imwrite(saveFile, cropped_image)
    if cropImg:
        return cropped_image
    else:
        return padded_image

此功能为裁剪图像并用灰色填充不足的部分。添加了保存功能,默认不使用。

实验结果:

裁剪图像并用灰色填充

拼接

def Stitcher_image(image_paths):
    stitcher = cv2.Stitcher_create()
    images = []
    for path in image_paths:
        img = cv2.imread(path)
        if img is not None:
            images.append(img)
    if len(images) < 2:
        print('至少需要两个图像进行拼接')
        return
    (status, stitched_image) = stitcher.stitch(images)
    if status == cv2.Stitcher_OK:
        return stitched_image
    else:
        print('图像拼接失败')

输入图片路径组成的列表,数量大于等于2才可进行拼接。下图是经过裁剪后保存的图片,原图片似乎因为较小,拼接时无法成功,经过放大再裁剪后拼接,实验成功。

实验结果: 

拼接的图像

随机调整参数

当然,上面只是简单的功能实现,现在我们需要对其添加随机参数。添加随机参数可以增加数据增强的多样性。通过在图像处理过程中引入随机性,可以使得每次处理的结果略有不同,从而扩展数据集的多样性。这对于训练深度学习模型非常有益,可以帮助模型更好地泛化和适应不同的输入。

d.随机翻转算法

介绍:通过随机选择是否对图像进行翻转,并选择翻转的方式(水平翻转或垂直翻转)来改变图像的方向或视角。

import cv2
import numpy as np
import pyps.pyzjr.utility as zjr

path = r'Images\Leopard_cat.png'
img = cv2.imread(path)
def horizontal_flip(image, axis):
    if axis != 2:
        image = cv2.flip(image, axis)
    return image

def random_generate():
    values = [0, 1, -1, 2]
    return np.random.choice(values)

def random_flip_batch(images):
    imglist=[]
    for img in images:
        random_value = random_generate()
        image=horizontal_flip(img,random_value)
        imglist.append(image)
    return imglist

if __name__ == "__main__":
    flipped_images=random_flip_batch([img,img,img,img])
    stackimg=zjr.stackImages(1,flipped_images)
    cv2.imshow("img",stackimg)
    cv2.waitKey(0)

随机图像翻转,只进行水平和垂直两个角度。

e.随机颜色明暗调整算法

介绍:通过随机选择图像的区域进行裁剪,以改变图像的大小和内容。

import cv2
import numpy as np
import pyps.pyzjr.utility as zjr
from d2l import torch as d2l
import random

path = r'Images\Leopard_cat.png'
img = cv2.imread(path)

def random_generate(mode):
    if mode=='flip':
        values = [0, 1, -1, 2]
        randimg=np.random.choice(values)
        return randimg
    if mode=='bright':
        bri_num = round(random.uniform(0.5, 1.5), 1)
        return bri_num

def Adjusted_image(img, brightness_factor=1.5):
    image_float = img.astype(np.float32)
    adjusted_image = image_float * brightness_factor
    adjusted_image = np.clip(adjusted_image, 0, 255)
    adjusted_image = adjusted_image.astype(np.uint8)
    return adjusted_image

def random_brightness_batch(images):
    imglist = []
    for img in images:
        random_value=random_generate("bright")
        image=Adjusted_image(img,random_value)
        imglist.append(image)
    return imglist

 随机颜色明暗调整,明暗变化在0.5到1.5之间随机变化。

f.随机裁剪算法

介绍:通过随机调整图像中每个像素的颜色明暗度,以改变图像的整体色调。

import cv2
import numpy as np
import pyps.pyzjr.utility as zjr
from d2l import torch as d2l
import random

path = r'Images\Leopard_cat.png'
img = cv2.imread(path)
def random_generate(img,mode):
    if mode=='flip':
        values = [0, 1, -1, 2]
        randimg=np.random.choice(values)
        return randimg
    elif mode=='bright':
        bri_num = round(random.uniform(0.5, 1.5), 1)
        return bri_num
    elif mode=='cut':
        scale = round(random.uniform(0.1, 1.0), 1)
        h,w=img.shape[:2]
        newH=random.randint(0, h)
        newW=random.randint(0, w)
        initPoint =[newW,newH]
        return initPoint,scale
    else:
        print("这并不是在选定规格内 This is not within the selected specifications.")

def Cut_image(image, coordinate, Leath, cropImg=False ,save=False, saveFile=''):
    imageH,imageW=image.shape[:2]
    x, y = coordinate[0], coordinate[1]
    width, height = Leath[0], Leath[1]
    h, w = height, width
    if x < 0:
        x = 0
    if y < 0:
        y = 0
    if x + width > imageW:
        width = imageW - x
    if y + height > imageH:
        height = imageH - y

    cropped_image = image[y:y + height, x:x + width]
    padded_image = np.full((h, w, 3), 128, dtype=np.uint8)
    x_offset = (w - width) // 2
    y_offset = (h - height) // 2
    padded_image[y_offset:y_offset + height, x_offset:x_offset + width] = cropped_image
    if save:
        cv2.imwrite(saveFile, cropped_image)
    if cropImg:
        return cropped_image
    else:
        return padded_image

def random_Cropping_batch(images):
    imglist = []
    for img in images:
        h, w = img.shape[:2]
        InitPoint, scale = random_generate(img, "cut")
        newH, newW = h * scale, w * scale

        image = Cut_image(img,InitPoint,[int(newH), int(newW)],cropImg=True)
        restored_image=cv2.resize(image,(w, h))
        imglist.append(restored_image)
    return imglist

if __name__ == "__main__":
    flipped_images=random_Cropping_batch([img, img, img, img])
    stackimg=zjr.stackImages(1,flipped_images)
    cv2.imshow("img",stackimg)
    cv2.waitKey(0)

随机裁剪图像,并且将原来的裁剪的图像还原为原来大小。

实验分析

实验图片:300x300,Leopard_cat.png

梅狸猫

本次实验采用一张300x300大小的梅狸猫图片进行实验,并进行了图像旋转、图像亮度调整以及图像裁剪与拼接,效果均达到我的预期,在图像裁剪的过程中,因为考虑到做的是数据增广,所以添加了灰度条,保证裁剪后的图片大小与原始图片相同;拼接的图片似乎不能太小,可能会拼接失败,本实验经过图片进行放大后裁剪后拼接,实验成功。

而在后面又添加了随机调整参数,有助于丹友们对图像增广的应用的理解。

关于拼接出现黑边的分析:

在实验过程中,我们注意到拼接后的图像边缘可能会出现一些黑边。这是由于图像拼接算法的工作原理所致,它会尝试将图像进行平滑过渡,以便在拼接处产生较少的不连续性。在一些情况下,这可能会导致边缘处的像素值略微偏暗,从而形成黑边。

虽然这些黑边可能对整体图像的观感产生一些影响,但通常情况下它们并不会严重干扰图像的内容。如果你认为黑边对你的应用场景有较大影响,您可以尝试进行后处理来减轻或消除黑边的影响。如边缘增强、图像修复或边缘填充等,来改善黑边问题。

总的来说,尽管在图像拼接过程中可能会出现一些黑边,但这并不会严重影响整体的拼接结果。通过适当的后处理方法,我们可以进一步改善图像的外观,并获得更好的拼接效果。

本章小结

本章介绍了图像处理中常见的几种操作:旋转、亮度调整、裁剪、拼接等。通过使用OpenCV和NumPy库的函数,轻松地实现了。

  • 首先,通过cv2.getRotationMatrix2D和cv2.warpAffine函数,我们可以指定旋转中心、旋转角度和缩放比例来旋转图像。
  • 接下来,将图像转换为浮点数类型,我们可以通过乘以亮度因子并将像素值控制在0到255之间来调整图像亮度。
  • 然后,通过指定裁剪区域的坐标和长度,我们可以裁剪出我们需要的图像,并使用灰色填充图像的不足部分。
  • 最后,使用cv2.Stitcher_create和stitch函数,我们可以将多张图像拼接在一起,从而创建一个更大的图像。在拼接过程中,我们需要注意边缘区域可能会有黑边的问题,可以使用图像裁剪来去除。

以上这些操作是图像处理中非常基础的操作,在实际应用中也非常常见。掌握这些基础操作后,我们可以更加轻松地实现更复杂的图像处理算法。

参考文章

(3条消息) 对图像进行随机翻转和裁剪_半个夏天1314的博客-CSDN博客

说明:本章节的代码均为草稿,如果想要这一章整理好的代码,可以私信我。 

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

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

相关文章

win10系统cpu版本 Tensorflow2.5.0的安装

文章目录 前言电脑重装系统了&#xff0c;顺便简单记录一下我的tensorflow2.5.0 CPU的安装过程 一、创建一个虚拟环境&#xff1f;二、确定 输入 y三、激活你的环境四、安装tensorflow2.5.0五、利用清华镜像源加速一下&#xff0c;不然等到猴年马月&#xff01;六&#xff0c;开…

Shape-E:文字到3D的生成模型试用

文章目录 Shape-E&#xff1a;文字到3D的生成模型试用项目介绍项目地址项目使用试用Text to 3DImage to 3D 总结 Shape-E&#xff1a;文字到3D的生成模型试用 项目介绍 Shape-E是一个生成3D模型的工具&#xff0c;可以通过输入文字或者上传图片生成3D模型。该模型的项目地址是…

穿越火线(CF) AI 自瞄 代码 权重 数据集 亲测可用(结尾有资源)

初衷 本人热衷玩CF&#xff0c;同时为一名程序员&#xff0c;近期听说AI霸占FPS游戏&#xff0c;本着学习的态度&#xff0c;特来测试 不喜欢看过程的小伙伴直接看最下面 模型 采用yolov5模型架构 对过程感兴趣的小伙伴下文自行学习 https://zhuanlan.zhihu.com/p/17212138…

数字孪生技术在矿业领域怎样应用?

随着科技的不断发展&#xff0c;数字孪生技术正逐渐走入矿业领域&#xff0c;为这个传统行业带来了全新的变革和机遇。数字孪生技术以其精准模拟和实时监控的特性&#xff0c;为矿业企业提供了更高效、更安全的运营和管理方式。 在矿业开采过程中&#xff0c;数字孪生技术的应…

代码随想录算法训练营day42 | 01背包问题,你该了解这些!,01背包问题,你该了解这些! 滚动数组 , 416. 分割等和子集

代码随想录算法训练营day42 | 背包理论基础&#xff0c;背包理论基础&#xff08;滚动数组&#xff09;&#xff0c; 416. 分割等和子集 1、01背包理论基础背包问题概述01背包二维dp数组01背包案例 2、01背包理论基础&#xff08;滚动数组&#xff09;3、 416. 分割等和子集解…

Redis持久化-Redis主从-Redis哨兵-Redis分片集群

主要内容 Redis持久化Redis主从Redis哨兵Redis分片集群 Redis持久化 Redis有两种持久化的方案: RDB持久化AOF持久化 1. RDB持久化 RDB全称Redis Database Backup file&#xff08;Redis数据备份文件&#xff09;&#xff0c;也被叫做Redis数据快照。简单来说就是把内存中的所…

数字化时代下,制造业企业应该这样做仓库管理

透过现象看本质&#xff0c;在传统的仓储管理中都存在着以下问题&#xff1a; 1.信息化水平较低&#xff0c;以人工为主&#xff0c;以纸张为主&#xff0c;效率低下&#xff0c;容易出现错误&#xff1b; 2.信息流的不对称性&#xff0c;各个过程之间的联系不紧密&#xff0c;…

【高危】Apache Spark UI shell 命令注入漏洞(POC)

漏洞描述 该漏洞是针对此前CVE-2022-33891漏洞的修订&#xff0c;原有漏洞通告中认为3.1.3版本已修复该漏洞&#xff0c;后发现仍受到影响&#xff0c;3.1.3版本已不再维护&#xff0c;官方建议升级至3.4.0版本。 Apache Spark是美国阿帕奇&#xff08;Apache&#xff09;软件…

在这里总有一款高温介电温谱仪适合您(GWJDN-300/600/1000型多种可选)

GWJDN-300型多用途型高温介电温谱仪 关键词&#xff1a;高温介电&#xff0c;变温&#xff0c;电容&#xff0c;损耗 GWJDN-300高温介电温谱仪是一款专门用于评估电介质材料高温介电机制&#xff08;材料极化、储能、驰豫、相变、微结构变化、分子团重新取向等&#xff09;的…

远程控制电脑怎么弄? 远程控制电脑方法介绍

如何免费远程控制电脑&#xff1f; “你好&#xff0c;你知道任何可靠的免费Windows远程控制软件吗&#xff1f;我需要在工作电脑和家用电脑之间进行远程控制&#xff0c;因为我将出差数周。有什么好用的远程控制电脑方法吗&#xff1f;提前致谢&#xff01;” 电脑之间如何…

ChatGPT学习指南

主旨 大家好&#xff0c;我是五竹。心血来潮整理了这份手册并且将为小白们持续更新和GPT相关的资源和教程&#xff0c;专注于打造一部最好的GPT入门指南。此文档永久免费在线查看&#xff0c;欢迎大家转发、收藏、点赞支持&#xff01;后面会在文档中更新&#xff1a;ChatGPT学…

优秀互联网产品经理必备的10张业务图谱

作为离产品最近的人&#xff0c;产品经理是团队的交通枢纽&#xff0c;链接运营的需求和程序员的开发工作。面对庞杂多面的工作&#xff0c;今天小编和大家聊聊产品经理在工作各环节想要精进专业&#xff0c;都需要具备哪些能力。 01学习篇 持续学习的概念早已被大家接受&#…

海量数据同步到DDM(oracle到mysql)

1、由于oracle的rownum性能&#xff0c;所以通过主键ID实现分页&#xff1b; 2、数据可能存在重复&#xff0c;批量插入mysql使用insert ignore语法&#xff1b; 3、DDM数据库&#xff0c;过千万后并发插入&#xff0c;性能就很差&#xff1a;采用单线程一千条批量插入&#…

MySQL--索引--0427--0507

目录 1. MySQL是如何处理数据的 2. MySQL与磁盘的关系 3. MySQL与磁盘交互的基本单位 4.MySQL和磁盘之间联系的总结 5.索引的理解 5.1 理解单个page 5.2 理解多个page 5.3 为什么采用B树 5.4 聚簇索引 和 非聚簇索引 5.5 聚簇索引 和 非聚簇索引下的普通索引 6.索引操作…

Spring 注解之@RestController与@Controller的区别

目录 1&#xff1a;介绍 2&#xff1a;区别 3&#xff1a;总体来说 4&#xff1a;社区地址 1&#xff1a;介绍 RestController 和 Controller 是 Spring MVC 中常用的两个注解&#xff0c;它们都可以用于定义一个控制器类。 2&#xff1a;区别 返回值类型不同&#xff1a;…

STM32单片机声控语音识别RGB彩灯多种模式亮度可调WS2812彩灯

实践制作DIY- GC0129-语音识别RGB彩灯 一、功能说明&#xff1a; 基于STM32单片机设计-语音识别RGB彩灯 二、功能介绍&#xff1a; STM32F103C系列最小系统板5VUSB电源64个灯珠的WS2812灯板1个开关键&#xff08;3档亮度调节&#xff09;1个模式切换键&#xff08;白灯 红灯…

软件测试4年从外包15K跳槽去字节 38K+12,啃完这份笔记你也可以

转行做软件测试已经是第4个年头&#xff0c;一直是一个不温不火的小职员&#xff0c;本本分分做着自己的事情&#xff0c;觉得自己的工作已经遇到了瓶颈&#xff0c;一个偶然的机会&#xff0c;获得了一份软件测试全栈知识点学习笔记&#xff0c;通过几个月的学习&#xff0c;5…

git提交代码到GitLab步骤及拉取远程分支内容

一、本地建立一个空文件夹 点击鼠标右键点击红色箭头方向 Git Hash Here 二、git init 进行初始化 这个时候文件夹中会出现 .git 文件夹 三、添加远程仓库地址 git remote add origin (address) # 添加远程仓库地址 address是远程仓库代码链接 四、如果有分支把远程分支拉到…

跨设备开发的未来:多端能力服务统一技术

多端能力服务统一&#xff08;Multi-Experience Service Orchestration&#xff0c;MESO&#xff09;是一种技术和服务架构的概念&#xff0c;旨在为多种终端设备提供统一的用户体验和功能。它解决了在不同终端设备上使用不同应用程序和服务时出现的问题&#xff0c;使得用户可…

Springboot +Flowable,会签、或签简单使用(二)

一.简介 **会签&#xff1a;**在一个流程中的某一个 Task 上&#xff0c;这个 Task 需要多个用户审批&#xff0c;当多个用户全部审批通过&#xff0c;或者多个用户中的某几个用户审批通过&#xff0c;就算通过。 例如&#xff1a;之前的请假流程&#xff0c;假设这个请假流程…