python:opencv进行文件夹文件模板匹配

📚博客主页:knighthood2001

公众号:认知up吧 (目前正在带领大家一起提升认知,感兴趣可以来围观一下)

🎃知识星球:【认知up吧|成长|副业】介绍
❤️如遇文章付费,可先看看我公众号中是否发布免费文章❤️
🙏笔者水平有限,欢迎各位大佬指点,相互学习进步!

适用情况

你有一个模板图片,你需要在某一个文件夹中,找到你这个文件。

完整代码

python 复制代码
import cv2
import os

def save_matched_images(original_image_path, folder_path, save_folder, val=0.8):
    """
    保存与模板图像匹配的图片到指定文件夹。

    Args:
        original_image_path (str): 原始模板图像的文件路径。
        folder_path (str): 需要遍历查找匹配图片的文件夹路径。
        save_folder (str): 保存匹配到的图片的目标文件夹路径。
        val (float, optional): 匹配程度的阈值。当匹配程度高于该值时,保存图片。默认为0.8。

    Returns:
        None

    """
    # 读取原始图像作为模板
    original_image = cv2.imread(original_image_path, 0)
    if original_image is None:
        print(f"Error: Failed to read original image from '{original_image_path}'.")
        return

    # 获取原始图像的尺寸
    template_height, template_width = original_image.shape[:2]

    # 创建保存结果的文件夹
    if not os.path.exists(save_folder):
        os.makedirs(save_folder)

    # 遍历文件夹中的每张图片
    for filename in os.listdir(folder_path):
        if filename.endswith(('.png', '.jpg', '.jpeg')):
            # 读取当前图片
            # image_path = folder_path + "\\" + filename
            image_path = os.path.join(folder_path, filename)
            print("image_path", image_path)
            current_image = cv2.imread(image_path, 0)
            if current_image is None:
                print(f"Warning: Failed to read image '{image_path}', skipping.")
                continue

            # 检查当前图片尺寸是否小于模板图像尺寸
            current_height, current_width = current_image.shape[:2]
            if current_height < template_height or current_width < template_width:
                print(f"Warning: Image '{filename}' size is smaller than template, skipping.")
                continue

            # 使用 TM_CCOEFF_NORMED 方法进行模板匹配
            result = cv2.matchTemplate(current_image, original_image, cv2.TM_CCOEFF_NORMED)

            # 获取匹配位置和匹配程度
            min_val, max_val, min_loc, max_loc = cv2.minMaxLoc(result)

            # 如果匹配程度高于0.8,则保存该图片
            if max_val > val:
                # 保存匹配的结果图片到指定文件夹
                matched_image = cv2.imread(image_path)
                save_path = os.path.join(save_folder, filename)
                cv2.imwrite(save_path, matched_image)
                print(f"Saved matched image: {save_path}")
            else:
                print(f"Warning: Image '{filename}' does not match template.")

# # 测试示例
original_image_path = '22.png'
folder_path = 'y_project'
save_folder = 'result'

save_matched_images(original_image_path, folder_path, save_folder)

代码部分即插即用,一般不会有啥太大问题,我把模板图像大小小于你要匹配图像大小的情况给pass了,不然就会报错。

如何使用

22.png就是你的模板图片,y_project文件夹中存放的就是你需要从中找出匹配度高的图片,将其放在result文件夹中。

注意事项

  • 首先就是你的路径不要设置成中文,opencv遇到中文,可能会存在报错。
  • 模板匹配的图片,你不能去缩放,否则,匹配不上了。

模板匹配如果遇到缩放图怎么办

**模板匹配通常对图像的缩放比较敏感。**如果模板图像和待匹配图像的尺寸不一致,即待匹配图像是模板图像的缩放版本,那么直接使用标准的模板匹配方法可能无法得到满意的结果。以下是几种处理图像缩放问题的策略:

  1. 尺度归一化 :在匹配之前,将所有待匹配图像缩放到与模板图像相同的尺寸。这可以通过OpenCV的cv2.resize函数实现。

  2. 尺度不变特征匹配:使用尺度不变特征变换(Scale-Invariant Feature Transform, SIFT)或其变种,如SURF(加速稳健特征)或ORB(Oriented FAST and Rotated BRIEF),这些特征检测算法能够检测到图像中的特定特征,并且对图像的缩放、旋转和部分亮度变化具有鲁棒性。

  3. 多尺度模板匹配 :对模板图像进行多尺度变换,生成一系列不同尺寸的模板图像,然后对每个尺寸的模板进行模板匹配。这可以通过在cv2.matchTemplate函数中使用不同的模板尺寸来实现。

  4. 基于学习的匹配算法:使用基于机器学习或深度学习的图像匹配算法,这些算法可以在训练阶段学习到图像的尺度变化,并在测试阶段对不同尺度的图像进行匹配。

  5. 图像金字塔:构建待匹配图像的金字塔,然后从顶层(最小的图像尺寸)开始,逐层向下进行模板匹配。如果在顶层找到了匹配,就不需要在更小的尺度上继续搜索。

  6. 自适应阈值:根据图像的尺度变化调整匹配阈值。较大的图像可能需要更低的阈值来找到匹配。

  7. 特征匹配后几何变换:使用特征匹配算法找到关键点,然后根据关键点之间的对应关系计算出最佳的仿射变换或透视变换,将待匹配图像变换到与模板图像相同的尺寸和方向。

选择哪种方法取决于你的具体应用场景和需求。例如,如果你知道图像只会发生轻微的缩放,可能只需要简单的尺度归一化。如果你需要处理更复杂的情况,可能需要使用更高级的特征匹配算法。

相关推荐
奋斗的小花生几秒前
c++ 多态性
开发语言·c++
魔道不误砍柴功3 分钟前
Java 中如何巧妙应用 Function 让方法复用性更强
java·开发语言·python
闲晨6 分钟前
C++ 继承:代码传承的魔法棒,开启奇幻编程之旅
java·c语言·开发语言·c++·经验分享
_.Switch28 分钟前
高级Python自动化运维:容器安全与网络策略的深度解析
运维·网络·python·安全·自动化·devops
老猿讲编程33 分钟前
一个例子来说明Ada语言的实时性支持
开发语言·ada
Chrikk1 小时前
Go-性能调优实战案例
开发语言·后端·golang
幼儿园老大*2 小时前
Go的环境搭建以及GoLand安装教程
开发语言·经验分享·后端·golang·go
canyuemanyue2 小时前
go语言连续监控事件并回调处理
开发语言·后端·golang
杜杜的man2 小时前
【go从零单排】go语言中的指针
开发语言·后端·golang
测开小菜鸟2 小时前
使用python向钉钉群聊发送消息
java·python·钉钉