opencv计算机视觉学习笔记二

第三章 Opencv3处理图像

1 不同色彩空间的转换

计算机视觉中三种常见的色彩空间:

灰度

BGR

HSV(hue色调 saturation饱合度 value黑暗程度)

2 傅里叶变换

快速傅里叶变换fft

离散傅里叶变换dft

高通滤波器heigh passfilter

检测图像的某个区域,根据像素和周围像素的亮度差值来提升该像素亮度的滤波器

示例代码如下:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time : 2016/11/29 12:23
# @Author : Retacn
# @Site : 高通滤波器
# @File : heighPassFilter.py
# @Software: PyCharm

import cv2
import numpy as np
from scipy import ndimage

#自定义核
kernel_3x3 = np.array([[-1, -1, -1],
 [-1, 8, -1],
 [-1, -1, -1]])

kernel_5x5 = np.array([[-1, -1, -1, -1, -1, ],
 [-1, 1, 2, 1, -1],
 [-1, 2, 4, 2, -1],
 [-1, 1, 2, 1, -1],
 [-1, -1, -1, -1, -1]])

#读入图像,转换为灰度格式
img=cv2.imread('../test.jpg',cv2.IMREAD_GRAYSCALE)

#卷积
k3=ndimage.convolve(img,kernel_3x3)
k5=ndimage.convolve(img,kernel_5x5)

#高通过滤
blurred=cv2.GaussianBlur(img,(11,11),0)
g_hpf=img-blurred

#显示图像
cv2.imshow('3x3',k3)
cv2.imshow('5x5',k5)
cv2.imshow('g_hpf',g_hpf)
cv2.waitKey()
cv2.destroyAllWindows()

低通滤波器low pass filter

在像素与周围像素的亮度差值小于一个特定值时,平滑该像素的亮度

3 创建模块

Filters.py文件,示例代码如下:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time : 2016/11/29 12:58
# @Author : Retacn
# @Site : 滤波器
# @File : filters.py.py
# @Software: PyCharm

import cv2
import numpy as np
import Three.utils #自定义工具类

Utils.py文件

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time : 2016/11/29 12:59
# @Author : Retacn
# @Site : 工具类
# @File : utils.py.py
# @Software: PyCharm

import cv2
import numpy as np
from scipy import interpolate

4 边缘检测

常用函数

def Laplacian(src, 
 ddepth, 
 dst=None, 
 ksize=None, 
 scale=None, 
 delta=None, 
 borderType=None)

def Sobel(src, 
 ddepth, 
 dx,
 dy, 
 dst=None, 
 ksize=None, 
 scale=None, 
 delta=None, 
 borderType=None)

def Scharr(src, 
 ddepth, 
 dx, 
 dy, 
 dst=None, 
 scale=None, 
 delta=None, 
 borderType=None)

模糊滤波函数

1 平均
 
  
函数原型
def blur(src, #源图像
  ksize, #内核大小
  dst=None, #输出图像
  anchor=None, #中心锚点
  borderType=None)# 边界模式
2 高斯模糊
 
  
函数原型
def GaussianBlur(src, #输入图像
 ksize, #高斯滤波模版大小
 sigmaX, #横向滤波系数
 dst=None, #输出图像
 sigmaY=None,#纵向滤波系数 
 borderType=None)
 
  
3 中值模糊
def medianBlur(src, #源图像
 ksize, #中值滤波器的模版的大小
 dst=None)#输出图像
 
  
4 双边滤波
def bilateralFilter(src, #输入图像
 d, #每个像素邻域的直径
 sigmaColor, #颜色空间的标准偏差
 sigmaSpace, #坐标空间的标准偏差
 dst=None, #输出图像
 borderType=None)#边缘点插值类型

示例代码如下:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time : 2016/11/29 12:58
# @Author : Retacn
# @Site : 滤波器
# @File : filters.py.py
# @Software: PyCharm

import cv2
import numpy as np
import Three.utils #自定义工具类

def strokeEdges(src,
 dst,
 blurKsize=7,#中值滤波ksize
 edgeKsize=5):#Laplacian算子ksize
 if blurKsize>=3:
 #中值滤波
 blurredSrc=cv2.medianBlur(src,blurKsize)
 #修改为灰度颜色空间
 graySrc=cv2.cvtColor(blurredSrc,cv2.COLOR_BGR2GRAY)
 else:
 graySrc=cv2.cvtColor(src,cv2.COLOR_BGR2GRAY)
 cv2.Laplacian(graySrc,cv2.CV_8U,graySrc,ksize=edgeKsize)
 normalizedInverseAlpha=(1.0/255)*(255-graySrc)
 channels=cv2.split(src)
 for channel in channels:
 channel[:]=channel*normalizedInverseAlpha
 cv2.merge(channels,dst)

5 用定制内核作卷积

def filter2D(src, #输入图像
 ddepth, #图像深度
 kernel, #卷积核,单通道浮点矩阵
 dst=None, #输出图像
 anchor=None, #一个被滤波的点在核内的位置(中心)
 delta=None, 

borderType=None)#边界类型

如果要对每个通道使用不同的核,必须用split()和merge()

示例代码如下:

#!/usr/bin/env python
# -*- coding: utf-8 -*-
# @Time : 2016/11/29 12:58
# @Author : Retacn
# @Site : 滤波器
# @File : filters.py.py
# @Software: PyCharm

import cv2
import numpy as np
import Three.utils # 自定义工具类


# 一般的卷积滤波器
class VConvolutionFilter(object):
 def __init__(self, kernel):
 self._kernel = kernel

 def apply(self, src, dst):
 cv2.filter2D(src, -1, self._kernel, dst)


# 特定的锐化滤波器
class SharpenFilter(VConvolutionFilter):
 def __init__(self):
 kernel = np.array([[-1, -1, -1],
 [-1, 9, -1],
 [-1, -1, -1]])
 VConvolutionFilter.__init__(self, kernel)


# 边缘检测滤波器
class FindEdgesFilter(VConvolutionFilter):
 def __init__(self):
 kernel = np.array([[-1, -1, -1],
 [-1, 8, -1],
 [-1, -1, -1]])
 VConvolutionFilter.__init__(self, kernel)


# 模糊滤波器
class BlurFilter(VConvolutionFilter):
 def __init__(self):
 kernel = np.array([[0.04, 0.04, 0.04, 0.04, 0.04],
 [0.04, 0.04, 0.04, 0.04, 0.04],
 [0.04, 0.04, 0.04, 0.04, 0.04],
 [0.04, 0.04, 0.04, 0.04, 0.04],
 [0.04, 0.04, 0.04, 0.04, 0.04]])
 VConvolutionFilter.__init__(self, kernel)


# 脊状和浮雕效果
class EmbossFilter(VConvolutionFilter):
 def __init__(self):
 kernel = np.array([[-2, -1, 0],
 [-1, 1, 1],
 [0, 1, 2]])
 VConvolutionFilter.__init__(self, kernel)


def strokeEdges(src,
 dst,
 blurKsize=7, # 中值滤波ksize
 edgeKsize=5): # Laplacian算子ksize
 if blurKsize >= 3:
 # 中值滤波
 blurredSrc = cv2.medianBlur(src, blurKsize)
 # 修改为灰度颜色空间
 graySrc = cv2.cvtColor(blurredSrc, cv2.COLOR_BGR2GRAY)
 else:
 graySrc = cv2.cvtColor(src, cv2.COLOR_BGR2GRAY)
 cv2.Laplacian(graySrc, cv2.CV_8U, graySrc, ksize=edgeKsize)
 normalizedInverseAlpha = (1.0 / 255) * (255 - graySrc)
 channels = cv2.split(src)
 for channel in channels:
 channel[:] = channel * normalizedInverseAlpha
 cv2.merge(channels, dst)

6 修改应用

#!/usr/bin/env python

# -*- coding: utf-8 -*-

# @Time: 2016/11/28 14:45

# @Author: Retacn

# @Site: cameo实现,有两种启动方法: run() 和 onkeypress()

# @File: cameo.py

# @Software: PyCharm

import cv2

from Three import filters

from Two.cameo.managers importWindowManager,CaptureManager

class Cameo(object):

def __init__(self):

self._windowManager=WindowManager('Cameo',self.onkeypress)

self._captureManager=CaptureManager(cv2.VideoCapture(0),self._windowManager,True)

# self._curveFilter=filters.BGRPortraCurveFilter()

def run(self):

self._windowManager.createWindow()

while self._windowManager.isWindowCreated:

self._captureManager.enterFrame()

frame=self._captureManager.frame

# filters.strokeEdges(frame,frame)

# self._curveFilter.apply(frame,frame)

self._captureManager.exitFrame()

self._windowManager.processEvents()

def onkeypress(self,keycode):

'''

space-> 载图

tab->启动和停止视频录制

esc->退出应用

:param keycode:

:return:

'''

if keycode==32:#space

self._captureManager.writeImage('screenshot.png')

elif keycode==9:#tab

if not self._captureManager.isWritingVideo:

self._captureManager.startWritingVideo('screencast.avi')

else:

self._captureManager.stopWritingVideo()

elif keycode==27:#esc

self._windowManager.destroyWindow()

if __name__=='__main__':

Cameo().run()

7 canny边缘检测

示例代码如下:


import cv2
import numpy as np

#读入灰度图像
img=cv2.imread('../test.jpg',cv2.IMREAD_GRAYSCALE)
#边缘检测
cv2.imwrite('../canny.jpg',cv2.Canny(img,200,300))
#显示图像
cv2.imshow('canny',cv2.imread('../canny.jpg'))
cv2.waitKey()
cv2.destroyAllWindows()

8 轮廓检测


import cv2
import numpy as np

img=np.zeros((200,200,),dtype=np.uint8)
#将指定的区域设为白色
img[50:150,50:150]=255
#设定阈值
ret,thresh=cv2.threshold(img,127,255,0)
#查找轮廓
image,contours,hierarchy=cv2.findContours(thresh,cv2.RETR_TREE,cv2.CHAIN_APPROX_SIMPLE)
#更换颜色空间
color=cv2.cvtColor(img,cv2.COLOR_GRAY2BGR)
img=cv2.drawContours(color,contours,-1,(0,255,0),2)
cv2.imshow('contours',color)
cv2.waitKey()
cv2.destroyAllWindows()

9 边界框,最小矩形和最小闭圆的轮廓


import cv2
import numpy as np

img = cv2.pyrDown(cv2.imread('../contours.jpg', cv2.IMREAD_UNCHANGED))

ret, thresh = cv2.threshold(cv2.cvtColor(img.copy(),
 cv2.COLOR_BGR2GRAY),
 127,
 255,
 cv2.THRESH_BINARY)
image, contours, hier = cv2.findContours(thresh,
 cv2.RETR_EXTERNAL,
 cv2.CHAIN_APPROX_SIMPLE)

for c in contours:
 #绘制矩形边界框
 x, y, w, h = cv2.boundingRect(c)
 cv2.rectangle(img, (x, y), (x + w, x + y), (0, 255, 0), 2)

 #绘制最小矩形(红色)
 rect=cv2.minAreaRect(c)
 box=cv2.boxPoints(rect)
 box=np.int0(box)
 cv2.drawContours(img,[box],0,(0,0,255),3)

 #绘制小最闭圆
 (x,y),radius=cv2.minEnclosingCircle(c)
 center=(int(x),int(y))
 radius=int(radius)
 img=cv2.circle(img,center,radius,(0,255,0),2)
cv2.drawContours(img,contours,-1,(255,0,0),1)
cv2.imshow('contours',img)
cv2.waitKey()
cv2.destroyAllWindows()

10 凸轮廓与douglas-peucker

示例代码如下:


import cv2
import numpy as np

#读入图像
img=cv2.pyrDown(cv2.imread('../contours.jpg'),cv2.IMREAD_UNCHANGED)
#修改颜色空间,设置阈值
ret,thresh=cv2.threshold(cv2.cvtColor(img.copy(),cv2.COLOR_BGR2GRAY),
 127,
 255,
 cv2.THRESH_BINARY)
#更换颜色空间
black=cv2.cvtColor(np.zeros((img.shape[0],img.shape[1]),
 dtype=np.uint8),
 cv2.COLOR_GRAY2BGR)
#检测轮廓
image,contours,hier=cv2.findContours(thresh,cv2.RETR_EXTERNAL,cv2.CHAIN_APPROX_SIMPLE)

for cnt in contours:
 #轮廓的周长
 epsilon=0.01*cv2.arcLength(cnt,True)
 approx=cv2.approxPolyDP(cnt,epsilon,True)
 hull=cv2.convexHull(cnt)

 cv2.drawContours(black,[cnt],-1,(0,255,0),2)#绿,精确的轮廓
 cv2.drawContours(black,[approx],-1,(255,255,0),2)#蓝色 近似多边形
 cv2.drawContours(black,[hull],-1,(0,0,255),2)#cv2.imshow('hull',black)
cv2.waitKey()
cv2.destroyAllWindows()

11 直线和圆检测

函数原型:

def HoughLinesP(image, #源图像
 rho, #线段的几何表示1
 theta, #np.pi/180
 threshold, #阈值
 lines=None, 
 minLineLength=None, #最小直线长度

maxLineGap=None)#最大线段间隙

直线检测,示例代码如下:


import cv2
import numpy as np

#读入图像
img=cv2.imread('../contours.jpg')
#转换颜色空间
gray=cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
#边缘检测
edges=cv2.Canny(gray,50,120)
#最小直线长度
minLineLength=100
#最大线段间隙
maxLineGap=5
#直线检测
lines=cv2.HoughLinesP(edges,#需要处理的图像
 1,
 np.pi/180,
 100,
 minLineLength,
 maxLineGap)

for x1,y1,x2,y2 in lines[1]:
 cv2.line(img,(x1,y1),(x2,y2),(0,255,0),2)

#显示图像
cv2.imshow('edges',edges)
cv2.imshow('lines',img)
cv2.waitKey()
cv2.destroyAllWindows()

圆检测,示例代码如下:


import cv2
import numpy as np

#读入图像
img=cv2.imread('../circles.jpg')
#更换颜色空间
gray=cv2.cvtColor(img,cv2.COLOR_BGR2GRAY)
#中值边滤
imgMb=cv2.medianBlur(gray,5)

#圆检测
circles=cv2.HoughCircles(imgMb,
 cv2.HOUGH_GRADIENT,
 1,
 120,
 param1=100,
 param2=30,
 minRadius=0,
 maxRadius=0)
circles=np.uint16(np.around(circles))

for i in circles[0,:]:
 cv2.circle(img,(i[0],i[1]),i[2],(0,255,0),2)
 cv2.circle(img,(i[0],i[1]),2,(0,0,255),3)

cv2.imwrite('../houghCircles.jpg',img)
cv2.imshow('../houghCircles.jpg',img)
cv2.waitKey()
cv2.destroyAllWindows()

12 检测其他形状

可以使用approxPloyDP

Cv2.findContours和cv2.approxyDP

你可能感兴趣的:(opencv计算机视觉学习笔记二)