opencv之图片处理看这一篇就够了(一)

如果文章对你有所帮助的话,能够给我个五星票吗~拜谢

https://bbs.csdn.net/topics/611391073

因为最近公司项目需要用到opencv对图像进行处理,所以对这一块进行了学习,现在将自己学习到的东西记录下来,以便使用。

一、图像读取与显示

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
cv2.imshow("soble",img)
cv2.waitKey(10000)

但是这里有个坑,如果是中文路径,你就会发现图片读取不出来,需要换个方法

#path为图片路径
img_np = np.fromfile(path, dtype = np.uint8)   
imgs = cv2.imdecode(img_np, -1) 

二、图像处理基础

1.像素处理

读取像素

读取图片像素时,如果图片为灰度图像则返回的为灰度值,如果是BGR图像,返回值为B,G,R的值。

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
#如果为灰度图像则只有一个返回值,如果BGR图像返回三个值
p = img[11,11]
print(p)

 正常情况下彩色图片返回的为BGR三通道的值,如果想单独获取某一个通道值则在位置后面加上通道

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
#如果为灰度图像则只有一个返回值,如果BGR图像返回三个值,如果加上通道值则只返回当前通道的值【0,1,2】代表蓝绿红三个通道
blue = img[11,11,0]
#此时返回蓝色通道值
print(blue)

green = img[11,11,1]
#此时返回绿色通道值
print(green)


red = img[11,11,2]
#此时返回红色通道值
print(red)

修改像素值

 如果为灰度图像则修改方式为:

img[11,11] = 255

如果为BGR图像则修改方式为:

img[11,11] = [255,255,255]

或者

img[11,11,0] = 255

img[11,11,1] = 255

img[11,11,2] = 255

2.使用numpy访问

读取像素 

 这个操作大致上获取像素值跟上面是完全相似的。也是分为灰度图片和BGR图片两种,返回值也是一样的。如果是灰度图片则只返回一个值,如果是BGR图片则返回三个值

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
blue = img.item(78,125,0)
green = img.item(78,125,1)
red = img.item(78,125,2)
print(blue)
print(green)
print(red)

修改像素值

 相比于不使用numpy,numpy对像素的设置更加方便。

操作方式如下:

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
#灰度图像:接收两个参数,第一个参数为像素位置,第二个位置为像素值
img.itemset((88,99),255)


#BGR图像  也是接收两个参数,第一个参数为像素位置,但是多了一个通道,第二个为像素值
img.itemset((88,99,0),255)
img.itemset((88,99,0),255)
img.itemset((88,99,0),255)

3.获取图像属性

opencv获取图像的属性包含三个方面

  • 形状:行、列、通道数
  • 像素数目
  • 图像的数据类型

1.形状

shape可以获取图像的形状

返回包含行数,列数,通道数的元组。如果是灰度图像则返回行数和列数,如果是BGR图像则返回行数、列数、通道数

import cv2
import numpy as np

#读取图像
img = cv2.imread("soble.png")
#将图像转为灰度图像
gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)

print(img.shape)    #输出值为(428, 605, 3)

print(gray.shape)  #输出值为(428, 605)

 2.像素数目

 size可以获取图像的像素数目

如果是灰度图像返回行数*列数,如果是BGR图像则返回行数*列数*通道数目

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)

print(img.size)    #输出值为776820
print(gray.size)   #输出值258940

 可以看出将图片转为灰色图像后,图片只剩下一个通道,相比于BGR图片像素减少了很多

3.图像类型

 dtype返回的是图像的数据类型

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)

print(img.dtype)   #uint8
print(gray.dtype)  #uint8

4.感兴趣区域(ROI)

ROI(region of interest),感兴趣区域

从被处理的图像以方框、圆、椭圆、不规则多边形等方式勾勒出需要处理的区域。

可以通过各种算子(operator)和函数来求得感兴趣区域ROI,并进行图像的下一步处理。

import cv2
import numpy as np
 
img = cv2.imread("soble.png")

cv2.imshow('ori',img)

temp = img[100:300,100:300]
img[100:300,400:600] = temp

cv2.imshow('temp',img)
cv2.waitKey()
cv2.destroyAllWindows()

 

5.通道的拆分与合并

1.拆分通道

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
cv2.imshow('ori',img)

b = img[:,:,0]
g = img[:,:,1]
r = img[:,:,2]
cv2.imshow('b',b)
cv2.imshow('g',g)
cv2.imshow('r',r)
cv2.waitKey()
cv2.destroyAllWindows()

也可以采用opencv提供的工具类进行通道拆分

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
cv2.imshow('ori',img)

b,g,r = cv2.split(img)
cv2.imshow('b',b)
cv2.imshow('g',g)
cv2.imshow('r',r)
cv2.waitKey()
cv2.destroyAllWindows()

 两种拆分方式结果相同,展示如下:

2.合并通道 

 通过opencv提供的工具类进行操作

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
cv2.imshow('ori',img)
b,g,r = cv2.split(img)
result = cv2.merge([b,g,r])
cv2.imshow('result',result)
cv2.waitKey()
cv2.destroyAllWindows()

 可以看到合并后和拆分之前的图像一致。

三、图像运算

1.图像加法

Numpy加法

numpy加法采用取模加法,如果两个像素相加,当像素值小于255时则取当前相加的像素值,如果相加的像素值大于255的话则拿当前像素值对255取模

OpenCV加法

OpenCV加法采用饱和运算加法,运算方式: 结果 = cv2.add(图像1,图像2)

采用饱和运算相加时,如果相加像素值低于255则取当前相加像素值,如果相加像素值大于255则取255作为当前像素值。

 需要注意的问题(参与运算的图像大小、类型必须一致)

下面代码来操作一下:

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
img = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
cv2.imshow('ori',img)
a = img + img
b = cv2.add(img,img)
cv2.imshow('a',a)
cv2.imshow('b',b)
cv2.waitKey()
cv2.destroyAllWindows()

可以看出来这个图像直接相加存在很大问题,相加以后图片跟原来的图片差别很大。所以接下来要介绍的是比较常用的图像融合。相比于这个简单的图像相加效果会更好。

2.图像融合

 结果图像 = 图像1*系数1 + 图像2* 系数2 + 亮度调节量

img = img1*0.3 + img2*0.7 +18

图像融合函数 addWeighted

dst = cv.addWeighted(src1,alpha,src2,beta,gamma)

dst = src1*alpha + src2*beta + gamma;

需要注意的是参数gamma不能省略

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
img = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
cv2.imshow('ori',img)
result = cv2.addWeighted(img,0.3,img,0.7,0)
cv2.imshow('result',result)
cv2.waitKey()
cv2.destroyAllWindows()

 经过试验发现,可以发现alpha和beta就是控制图片的显示占比,哪张图片的系数大,那么哪张图片就比较明显。

四、类型转换

将图像由一种类型转换为另外一种类型

OpenCV提供了200多种图片转换方式,有需要的参考官方文档即可

 举个简单的例子,就拿BGR转gray来说:

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
gray = cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
cv2.imshow('gray',gray)
cv2.waitKey()
cv2.destroyAllWindows()

五、几何变换

1.图像缩放

dst = cv2.resize(src,dsize)

disze 缩放大小

b = cv2.resize(a,(122,122))

 dst = cv2.resize(src,dsize,fx,fy)

fx,fy缩放大小,如果dsize不为空则按照dsize进行缩放,如果为空则按照fx,fy进行缩放

b = cv2.resize(a,None,fx=0.5,fy=0.7)

 代码示例:

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
rows,cols = img.shape[:2]
b=cv2.resize(img,(round(cols*0.5),round(rows*1.2)))
cv2.imshow('ori',img)
cv2.imshow('resize',b)
cv2.waitKey()
cv2.destroyAllWindows()

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
rows,cols = img.shape[:2]
b=cv2.resize(img,None,fx=1,fy=0.5)
cv2.imshow('ori',img)
cv2.imshow('resize',b)
cv2.waitKey()
cv2.destroyAllWindows()

2.图像翻转

dst = cv2.flip(src,flipCode)

flipCode = 0 以X为对称轴进行翻转

flipCode > 0 以y轴为对称轴进行翻转

flipCode < 0 以y轴为对称轴进行翻转,再以x轴为对称轴进行翻转

 代码示例:

import cv2
import numpy as np
 
img = cv2.imread("soble.png")
b= cv2.flip(img,0)
c= cv2.flip(img,1)
d= cv2.flip(img,-1)
cv2.imshow('ori',img)
cv2.imshow('b',b)
cv2.imshow('c',c)
cv2.imshow('d',d)
cv2.waitKey()
cv2.destroyAllWindows()

由于时间原因,今天先写到这里剩余部分有时间会接着写。

  • 43
    点赞
  • 316
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值