MyOpenCV-learning-图像基本操作

图像的读取以及基本属性操作

  • RGB:三个通道,都知道哈。

数据读取-图像

  • cv2.imread(‘filepath’,flags):读入图像。

    • filepath为路径
    • flags为读入图片的标志
      • cv2.IMREAD_COLOR: 彩色图像, 忽略alpha通道,
      • cv2.IMREAD_GRAYSCALE: 灰度图像,0
      • cv2.IMREAD_UNCHANGED: 读入完整图片,包括alpha通道,
  • alpha通道:以后再说

上代码

import cv2    #opencv读取的格式是BGR(不是RGB格式)
import matplotlib.pyplot as plt
import numpy as np
%matplotlib inline

img = cv2.imread('cat.jpg')    #读取图片信息
img

array([[[184, 196, 200],
[184, 196, 200],
[184, 196, 200],
…,
[201, 203, 204],
[201, 203, 204],
[203, 202, 204]],

[[184, 196, 200],
[184, 196, 200],
[184, 196, 200],
…,
[201, 203, 204],
[201, 203, 204],
[204, 203, 205]],

[[185, 196, 200],
[185, 196, 200],
[185, 196, 200],
…,
[202, 204, 205],
[202, 204, 205],
[204, 203, 205]],

…,

[[203, 205, 205],
[203, 205, 205],
[203, 205, 205],
…,
[226, 225, 227],
[226, 225, 227],
[225, 224, 226]],

[[204, 206, 206],
[204, 206, 206],
[204, 206, 206],
…,
[226, 225, 227],
[226, 225, 227],
[225, 224, 226]],

[[201, 203, 203],
[202, 204, 204],
[202, 204, 204],
…,
[228, 226, 226],
[228, 226, 226],
[229, 226, 228]]], dtype=uint8)

注意
  • dtype值:8字节
  • 维度看中括号数,如上为3个维度。img 用[h,w,c]存储(高度,宽度,深度)。也就是说,第一维度就是高度;第二维度是宽度;第三维度就是最内层的中括号表示深度,也就是BGR了。在这里插入图片描述

图像的显示 以及 等待时间设定

  • 主要函数:cv2.show()

代码举例

#图像的显示,也可以创建多个窗口
cv2.imshow ('image',img)    #第一个参数是窗口的名字,其次为图像。

# cv2.imshow('image2',img)    #创建多个窗口

#等待时间,毫秒级,0表示 任意键 终止
cv2.waitKey(10000)

#删除任何我们建立的窗口
cv2.destroyAllWindows()

# cv2.destroyWindow('image')    #删除特定的窗口,在括号内输入想删除的窗口名
  • 注意,当放大窗口之后图片大小不变,想要改变怎么办,看下面的函数。
  • 调整图片大小的函数:cv2.namesWindow()
    • 初始设定函数标签为cv2.WINDOW_AUTOSIZE
    • 函数标签为cv2.WINDOW_NORMAL,即可调整窗口大小
cv2.namedWindow('image',cv2.WINDOW_NORMAL)
cv2.imshow('image',img)
cv2.waitKey(0)
cv2.destroyAllWindows()

想代码整洁,就设个函数呗,框起来就好啦

#执行上述三个函数的函数窗口
def cv_show(name,img):
    cv2.imshow(name,img)
    cv2.waitKey(0)
    cv2.destroyAllWindows()
img.shape

(225, 225, 3)

灰度图

上面讲过cv2.imread的flags,那cv2.IMREAD_GRAYSCALE就可以读取灰度图像了,既然没有RGB,所以就二维了呗

#灰度图的读取做法
img = cv2.imread('cat.jpg',cv2.IMREAD_GRAYSCALE)
img

array([[196, 196, 196, …, 203, 203, 203],
[196, 196, 196, …, 203, 203, 204],
[196, 196, 196, …, 204, 204, 204],
…,
[205, 205, 205, …, 226, 226, 225],
[206, 206, 206, …, 226, 226, 225],
[203, 204, 204, …, 226, 226, 227]], dtype=uint8)

img.shape

(225, 225)

#图像的显示,也可以创建多个窗口
cv2.imshow ('image',img)
#等待时间,毫秒级,0表示任意键终止
cv2.waitKey(10000)
cv2.destroyAllWindows()

其他的函数

保存
  • 注意看,文件中增加了新图片
cv2.imwrite("mycat.png",img)

True

格式
type(img)    #ndarray格式

numpy.ndarray

像素点个数
img.size    #size:像素点个数

50625

数据类型
img.dtype    #数据类型

dtype(‘uint8’)

使用Matplotlib

img = cv2.imread('cat.jpg')
plt.imshow(img,cmap = 'gray',interpolation='bicubic')
plt.xticks([]),plt.yticks([])
plt.show()

在这里插入图片描述

  • 图片有色差,原因是使用cv2.imread()接口读图像,读进来的是BGR格式以及【0~255】,所以将其转换为RGB格式即可
img_2 = img[:,:,[2,1,0]]
plt.imshow(img_2)

<matplotlib.image.AxesImage at 0x2608f2faef0>

在这里插入图片描述
欸嘿,神奇不。

数据读取-视频

视频由图象组成,成为帧,想必都知道。

  • cv2.VideoCapture可以捕获镜头,用数字来控制不同的设备,例如0,1

运行一下,不要被自己的大脸吓到哦(不是在说我自己

import numpy as np
import cv2
cap = cv2.VideoCapture(0)
while(True):
    ret, frame = cap.read()
    
    gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)
    
    cv2.imshow('frame',gray)
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

cap.release()
cv2.destroyAllWindows()
  • 保存视频
  • FourCC 编码
  • 从摄像头中捕获视频,沿水平方向旋转每一帧并保存它。
# import numpy as np
# import cv2

# cap = cv2.VideoCapture(0)

# # Define the codec and create VideoWriter object
# fourcc = cv2.cv.FOURCC(*'XVID')
# out = cv2.VideoWriter('output.avi',fourcc, 20.0, (640,480))

# while(cap.isOpened()):
#     ret, frame = cap.read()
#     if ret==True:
#         frame = cv2.flip(frame,0)

#         # write the flipped frame
#         out.write(frame)

#         cv2.imshow('frame',frame)
#         if cv2.waitKey(1) & 0xFF == ord('q'):
#             break
#     else:
#         break

# # Release everything if job is finished
# cap.release()
# out.release()
# cv2.destroyAllWindows()
  • 如果是视频文件,直接制定好路径即可
vc = cv2.VideoCapture('test.mp4')
#检查是否打开正确
if vc.isOpened():    #判断能否打开
    open, frame = vc.read()    #读取帧
else:
    open = False
while open:
    ret, frame = vc.read()
    if frame is None:
        break
    if ret == True:
        gray = cv2.cvtColor(frame, cv2.COLOR_BGR2GRAY)    #转换为灰度图
        cv2.imshow('result',gray)
        if cv2.waitKey(1) & 0xFF == 27:    #waitkey数值越大,播放速度越慢
            break
vc.release()
cv2.destroyAllWindows()

截取部分图像数据

可自己截取图片的部分

img = cv2.imread('cat.jpg')
cat = img[0:200,0:20]
cv_show('cat',cat)
b,g,r = cv2.split(img)
b

array([[184, 184, 184, …, 201, 201, 203],
[184, 184, 184, …, 201, 201, 204],
[185, 185, 185, …, 202, 202, 204],
…,
[203, 203, 203, …, 226, 226, 225],
[204, 204, 204, …, 226, 226, 225],
[201, 202, 202, …, 228, 228, 229]], dtype=uint8)

r.shape

(225, 225)

img = cv2.merge((b,g,r))
img.shape

(225, 225, 3)

只保留单个通道

  • R:G:B分别对应0:1:2

  • 将其余两项设置为零即可

#只保留R通道
cur_img = img.copy()
cur_img[:,:,0] = 0
cur_img[:,:,1] = 0
cv_show('R',cur_img)
#只保留G通道
cur_img = img.copy()
cur_img[:,:,0] = 0
cur_img[:,:,2] = 0
cv_show('G',cur_img)
#只保留B通道
cur_img = img.copy()
cur_img[:,:,1] = 0
cur_img[:,:,2] = 0
cv_show('B',cur_img)

边界填充

  • 卷积介绍,指路 https://mlnotebook.github.io/post/CNN1/ 了解一下

看代码注释,有讲解

top_size, bottom_size, left_size, right_size = (50,50,50,50)    #上下左右填充值

#复制法,复制最边缘像素
replicate = cv2.copyMakeBorder(img, top_size, bottom_size, left_size, right_size, borderType = cv2.BORDER_REPLICATE)

#反射法,对感兴趣的图像中的像素在两边进行赋值。例如: fedcba|abcdefgh|hgfedc
reflect = cv2.copyMakeBorder(img, top_size, bottom_size, left_size, right_size, borderType = cv2.BORDER_REFLECT)

#反射法,以最边缘像素为轴,对称。例如:gfedcb|abcdefgh|gfedcba
reflect101 = cv2.copyMakeBorder(img, top_size, bottom_size, left_size, right_size, borderType = cv2.BORDER_REFLECT_101)

#外包装法。例如:bcdefh|abcdefgh|abcdefg
wrap = cv2.copyMakeBorder(img, top_size, bottom_size, left_size, right_size, borderType = cv2.BORDER_WRAP)

#常量法,常数值填充
constant = cv2.copyMakeBorder(img, top_size, bottom_size, left_size, right_size, borderType = cv2.BORDER_CONSTANT, value = 700)#需设置value值,选择常数填充
import matplotlib.pyplot as plt
plt.subplot(231), plt.imshow(img, 'gray'), plt.title('ORIGINAL')
plt.subplot(232), plt.imshow(replicate, 'gray'), plt.title('REPLICATE')
plt.subplot(233), plt.imshow(reflect, 'gray'), plt.title('REFLECT')
plt.subplot(234), plt.imshow(reflect101, 'gray'), plt.title('REFLECT_101')
plt.subplot(235), plt.imshow(wrap, 'gray'), plt.title('WRAP')
plt.subplot(236), plt.imshow(constant, 'gray'), plt.title('CONSTANT')

plt.show()

在这里插入图片描述

数值计算

img_cat = cv2.imread('cat.jpg')
img_dog = cv2.imread('dog.jpg')
  • 加常数
img_cat2 = img_cat + 10    #所有像素值加10
img_cat[:5,:,0]

array([[184, 184, 184, …, 201, 201, 203],
[184, 184, 184, …, 201, 201, 204],
[185, 185, 185, …, 202, 202, 204],
[185, 185, 185, …, 202, 202, 205],
[185, 185, 185, …, 203, 203, 206]], dtype=uint8)

img_cat2[:5,:,0]

array([[194, 194, 194, …, 211, 211, 213],
[194, 194, 194, …, 211, 211, 214],
[195, 195, 195, …, 212, 212, 214],
[195, 195, 195, …, 212, 212, 215],
[195, 195, 195, …, 213, 213, 216]], dtype=uint8)

  • 两图片相加
(img_cat + img_cat2)[:5,:,0]    # 和 对256取余(像素值范围为0~255)

array([[122, 122, 122, …, 156, 156, 160],
[122, 122, 122, …, 156, 156, 162],
[124, 124, 124, …, 158, 158, 162],
[124, 124, 124, …, 158, 158, 164],
[124, 124, 124, …, 160, 160, 166]], dtype=uint8)

  • 调用cv2.add函数,将两图片相加,但是会越界,最后取最大值,注意一下
cv2.add(img_cat,img_cat2)[:5,:,0]    # add()函数,越界 取最大值

array([[255, 255, 255, …, 255, 255, 255],
[255, 255, 255, …, 255, 255, 255],
[255, 255, 255, …, 255, 255, 255],
[255, 255, 255, …, 255, 255, 255],
[255, 255, 255, …, 255, 255, 255]], dtype=uint8)

图像融合

  • 注意shape值,不同不能相加哟
img_cat + img_dog    #不可操作,两图像shape值不同,无法相加

ValueError Traceback (most recent call last)

in
----> 1 img_cat + img_dog #不可操作,两图像shape值不同,无法相加

ValueError: operands could not be broadcast together with shapes (225,225,3) (678,1024,3)

img_cat.shape

(225, 225, 3)

  • resize()函数,更改shape值
img_dog = cv2.resize(img_dog, (225,225))   
img_dog.shape

(225, 225, 3)

融合一下

res = cv2.addWeighted(img_cat, 0.7, img_dog, 0.3, 2)
plt.imshow(res)

<matplotlib.image.AxesImage at 0x20032e7fc18>

在这里插入图片描述

害 挺 好 看,是吧~

  • cv2.resize()可以调整图片的尺寸
res = cv2.resize(img,(0,0),fx = 1, fy = 3)
plt.imshow(res)

<matplotlib.image.AxesImage at 0x20032d1f518>
在这里插入图片描述

res = cv2.resize(img,(0,0),fx = 3, fy = 1)
plt.imshow(res)

<matplotlib.image.AxesImage at 0x20032e1bcc0>

在这里插入图片描述

就是这样了,可能还会补充,欢迎讨论。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
K-means clustering is a popular unsupervised machine learning algorithm used for clustering data points into distinct groups or clusters. In OpenCV-Python, you can perform K-means clustering using the `kmeans` function from the `cv2` module. Here is an example code snippet to demonstrate how to use K-means clustering in OpenCV-Python: ```python import cv2 import numpy as np # Load the image image = cv2.imread('image.jpg') # Reshape the image to a 2D array of pixels pixels = image.reshape(-1, 3) # Convert the pixel values to float32 pixels = np.float32(pixels) # Define the criteria for the algorithm (number of iterations and epsilon) criteria = (cv2.TERM_CRITERIA_EPS + cv2.TERM_CRITERIA_MAX_ITER, 10, 1.0) # Set the number of clusters k = 5 # Perform K-means clustering _, labels, centers = cv2.kmeans(pixels, k, None, criteria, 10, cv2.KMEANS_RANDOM_CENTERS) # Convert the centers to uint8 centers = np.uint8(centers) # Map each pixel to its corresponding cluster center segmented_image = centers[labels.flatten()] # Reshape the segmented image back to its original shape segmented_image = segmented_image.reshape(image.shape) # Display the original image and the segmented image cv2.imshow('Original Image', image) cv2.imshow('Segmented Image', segmented_image) cv2.waitKey(0) cv2.destroyAllWindows() ``` Make sure to replace `'image.jpg'` with the path to your own image. The code reads an image, reshapes it into a 2D array of pixels, performs K-means clustering, maps each pixel to its corresponding cluster center, and displays the original image and the segmented image. Feel free to ask if you have any further questions!

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值