文章目录
前言
随着科技的不断进步,自动化和智能化在工业生产中的应用越来越广泛。在钢材生产过程中,钢材表面缺陷检测是一个重要的环节,直接关系到产品的质量和生产效率。传统的表面缺陷检测方法依赖于人工操作,不仅效率低下,而且容易受到主观因素的影响,导致检测结果的不准确性。因此,开发一种高效、准确的钢材表面缺陷检测系统具有重要的现实意义。
一、算法实现流程:
本次项目主要目的是帮助大家掌握构建不同的结构元进行形态学变换,钢材图片为:
经过特征分析,算法实现流程为,二值化获取痕迹前景,前景去噪,形态学让痕迹连续并去除更多无用噪声,霍夫直线读取图像中的直线并绘制。
二,算法详解:
2.1 二值化与去噪
本次算法二值化使用的是opencv内置自适应二值化,与传统二值化相比其更能适应光照等特征干扰,函数名为cv2.adaptiveThreshold,cv2.adaptiveThreshold 是OpenCV库中的一个函数,用于对图像进行自适应阈值处理。自适应阈值处理与全局阈值处理不同,它不是使用一个固定的全局阈值值来二值化图像,而是根据图像中每个像素点周围的局部区域亮度来计算一个阈值。这种方法对于光照不均匀的图像特别有效。
输入:
src:输入的灰度图像。
maxValue:二值化后像素值的上限,通常是255。
adaptiveMethod:确定自适应方法。可能的值包括:
ADAPTIVE_THRESH_MEAN_C:使用邻域像素的平均值来计算阈值。
ADAPTIVE_THRESH_GAUSSIAN_C:使用邻域像素的加权平均值来计算阈值,权重取决于邻域像素与中心像素的亮度差。
thresholdType:阈值类型。可能的值包括:
THRESH_BINARY:像素值大于阈值的设置为最大值,小于阈值的设置为0。
THRESH_BINARY_INV:像素值大于阈值的设置为0,小于阈值的设置为最大值。
blockSize:计算局部阈值的邻域大小,必须是奇数。
C:常数,从平均值或加权平均值中减去。这个参数可以帮助调整阈值,使其更加适合特定场景。
输出参数:cv2.adaptiveThreshold 函数返回一个二值图像,其中像素点的值要么是0(黑色),要么是最大灰度值(白色)。
示例
python
thresh = cv2.adaptiveThreshold(gray, 255, cv2.ADAPTIVE_THRESH_MEAN_C, cv2.THRESH_BINARY, 11, -25)
效果:
图中的噪声很多,由于图像中的裂痕比较细,如果直接使用中值滤波会造成线段不连续,故采用高斯滤波并对滤波后的图像在进行二值化:
python
blurred = cv2.GaussianBlur(thresh, (15, 15), 0)
_, binary = cv2.threshold(blurred, 30, 255, cv2.THRESH_BINARY)
2.2 形态学处理
常态情况下,结构元的形状一般为宽高相等的多边形,但本次项目的特征为直线,故结构元的形状也定义为直线结构元,这样能在形态学变换中很好的保留本身形状:
代码实现:
python
# 定义结构元素
kernel = np.ones((1, 65), np.uint8)
kernel2 = np.ones((1, 15), np.uint8)
kernel3 = np.ones((1, 30), np.uint8)
# 应用形态学操作
morph = cv2.morphologyEx(binary, cv2.MORPH_CLOSE, kernel) # 应用闭运算
morph2 = cv2.morphologyEx(binary, cv2.MORPH_OPEN, kernel2) # 应用开运算
dia = cv2.dilate(morph2, kernel3) # 应用膨胀运算
效果:
最后只需要识别蒙版中的直线即可
三,整体代码实现:
python
# 导入OpenCV库和NumPy库
import cv2
import numpy as np
# 读取图像
img = cv2.imread(r'D:\AI_tool\GFPGAN-master\1.png') # 读取图片路径为D盘AI工具目录下的GFPGAN-master子目录中的1.png
gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # 将BGR格式的图像转换为灰度图像
# 应用自适应阈值处理
thresh = cv2.adaptiveThreshold(gray, 255, cv2.ADAPTIVE_THRESH_MEAN_C, cv2.THRESH_BINARY, 11, -25) # 计算每个像素点的局部阈值,并二值化图像
blurred = cv2.GaussianBlur(thresh, (15, 15), 0) # 对二值化图像进行高斯模糊处理
_, binary = cv2.threshold(blurred, 30, 255, cv2.THRESH_BINARY) # 再次二值化图像
cv2.imshow("thresh", thresh) # 显示第一次二值化后的图像
cv2.imshow("binary", binary) # 显示第二次二值化后的图像
# 定义结构元素
kernel = np.ones((1, 65), np.uint8)
kernel2 = np.ones((1, 15), np.uint8)
kernel3 = np.ones((1, 30), np.uint8)
# 应用形态学操作
morph = cv2.morphologyEx(binary, cv2.MORPH_CLOSE, kernel) # 应用闭运算
morph2 = cv2.morphologyEx(binary, cv2.MORPH_OPEN, kernel2) # 应用开运算
dia = cv2.dilate(morph2, kernel3) # 应用膨胀运算
# 设置HoughLinesP参数
threshold = 100
minLineLength = 15
maxLineGap = 20
# 应用HoughLinesP检测直线
lines = cv2.HoughLinesP(dia, 1, 30 * np.pi / 360, threshold, minLineLength, maxLineGap)
# 创建线性图像用于绘制检测到的直线
linear = img.copy()
# 遍历检测到的直线并绘制
for [line] in lines:
x1, y1, x2, y2 = line # 提取直线端点坐标
cv2.line(linear, (x1, y1), (x2, y2), (0, 0, 255), 1) # 在线性图像上绘制直线
# 显示原始图像和线性图像
cv2.imshow("ori", img)
cv2.imshow("linear", linear)
# 等待任意键按下
cv2.waitKey(0)
四:效果: