如何仅用腐蚀、膨胀、异或与阈值化提取图像中间骨骼(OpenCV)
提取图像中中间大骨骼的实现方案
问题背景
输入为灰度骨骼图像,当前处理后会同时显示三根骨骼,需求是仅保留中间的那根大骨骼。
解决步骤
核心思路是通过轮廓检测定位目标,再用掩码提取区域:
- 先对图像做二值化反转,让骨骼区域转为白色,方便轮廓识别
- 提取所有外部轮廓,通过轮廓的中心横坐标排序,直接选中中间的轮廓
- 生成仅包含中间轮廓的掩码,与原图像做位运算得到结果
完整代码
import cv2 as cv import numpy as np import matplotlib.pyplot as plt # 读取灰度图像 b = cv.imread('content/B.tif', cv.IMREAD_GRAYSCALE) # 二值化反转,让骨骼区域为白色 _, binary_b = cv.threshold(b, 200, 255, cv.THRESH_BINARY_INV) # 提取外部轮廓 contours, _ = cv.findContours(binary_b, cv.RETR_EXTERNAL, cv.CHAIN_APPROX_SIMPLE) # 计算每个轮廓的中心横坐标,排序后取中间的轮廓 contour_list = [] for cnt in contours: x, _, w, _ = cv.boundingRect(cnt) contour_list.append((x + w//2, cnt)) # 按中心x坐标排序,取中间项 contour_list.sort(key=lambda item: item[0]) middle_cnt = contour_list[1][1] # 三个轮廓,索引1对应中间的 # 创建掩码并绘制中间轮廓 mask = np.zeros_like(b) cv.drawContours(mask, [middle_cnt], -1, 255, cv.FILLED) # 提取目标区域 result = cv.bitwise_and(b, mask) # 展示结果 plt.figure(figsize=(5,5)) plt.imshow(result, cmap='gray') plt.axis('off') plt.show()
补充说明
- 若骨骼的面积差异明显,也可以通过轮廓面积筛选最大的那个(替换排序逻辑为按面积降序取第一个)
- 阈值可根据实际图像微调,确保骨骼与背景分离彻底
内容的提问来源于stack exchange,提问作者Rachit Anand
相关产品推荐
相关产品推荐

