使用 OpenCV 实现图像等比例填充或保持宽高比填充

对图像进行不变形填充(也称为等比例填充或保持宽高比填充)的意义在于在调整图像尺寸时避免图像内容失真,同时确保图像适配目标尺寸。这种操作通常在以下场景中具有重要价值:


1. 核心意义

(1)避免内容失真
  • 问题:直接缩放图像(如拉伸或压缩)会破坏原始宽高比,导致图像内容扭曲(如人脸变胖/变瘦、物体比例失调)。
  • 解决方案:通过不变形填充,先按比例缩放图像至目标尺寸的某一边(高度或宽度),再对另一边进行填充,从而保持原始内容比例
(2)适配固定尺寸的容器
  • 需求:在深度学习、图像处理或界面设计中,模型或框架可能要求输入图像具有固定尺寸(如224×224)。
  • 作用:填充可以统一图像尺寸,同时避免因强制缩放导致的关键信息丢失(如目标检测中物体变形)。

2. 典型应用场景

(1)深度学习模型输入
  • 目标检测/分类:模型通常需要固定尺寸的输入(如YOLO、ResNet)。不变形填充可确保图像比例不变,避免因拉伸导致的特征错位。
  • 对比示例
    • 错误方式:直接拉伸图像至224×224,导致人脸变形。
    • 正确方式:缩放图像至224×168(保持比例),再填充至224×224(上下填充黑色边框)。
(2)图像显示与排版
  • 需求:在网页或APP中展示图片时,需保持图片比例以避免视觉扭曲。
  • 作用:填充可确保图片在固定尺寸的容器中显示时,主体内容(如产品图、人像)保持正常比例。
(3)数据增强
  • 方法:在训练前对图像进行随机填充(如上下左右填充不同颜色),增加数据多样性。
  • 效果:提升模型对边缘区域的鲁棒性。

3. 技术实现细节

(1)计算缩放比例
  • 步骤
    1. 计算目标尺寸与原始尺寸的宽高比。
    2. 选择较小的缩放比例(min(target_height/orig_height, target_width/orig_width)),确保图像完整覆盖目标尺寸的某一边。
  • 示例
    • 原始图像:300×200,目标尺寸:224×224。
    • 计算比例:min(224/300, 224/200) = 0.746
    • 缩放后尺寸:300×0.746=224(宽),200×0.746=149(高)。
(2)填充计算
  • 步骤
    1. 计算缩放后图像与目标尺寸的差值(如高度差:224-149=75)。
    2. 将差值均分到两侧(如上下各填充37或38像素)。
  • 公式
     

    python

    height_padding = target_height - scaled_height
    top_pad = height_padding // 2
    bottom_pad = height_padding - top_pad
(3)填充颜色选择
  • 常见选项
    • 黑色/白色:简单且不影响主体内容。
    • 均值填充:用图像像素均值填充,减少边缘突兀感。
    • 随机填充:数据增强时使用,增加模型泛化性。

4. 代码示例(Python + OpenCV)

 

python

import cv2
import numpy as np

def resize_and_pad(image, target_shape, padding_color=(0, 0, 0)):
    """
    保持宽高比填充图像至目标尺寸
    :param image: 输入图像
    :param target_shape: (height, width)
    :param padding_color: 填充颜色 (B, G, R)
    :return: 填充后的图像
    """
    orig_height, orig_width = image.shape[:2]
    target_height, target_width = target_shape

    # 计算缩放比例
    scale = min(target_height / orig_height, target_width / orig_width)
    scaled_width = int(orig_width * scale)
    scaled_height = int(orig_height * scale)

    # 缩放图像
    resized = cv2.resize(image, (scaled_width, scaled_height), interpolation=cv2.INTER_LINEAR)

    # 计算填充
    width_pad = target_width - scaled_width
    height_pad = target_height - scaled_height
    left_pad = width_pad // 2
    right_pad = width_pad - left_pad
    top_pad = height_pad // 2
    bottom_pad = height_pad - top_pad

    # 填充图像
    padded = cv2.copyMakeBorder(resized, top_pad, bottom_pad, left_pad, right_pad, 
                               cv2.BORDER_CONSTANT, value=padding_color)
    return padded

# 示例使用
image = cv2.imread("input.jpg")  # 读取图像
padded_image = resize_and_pad(image, (224, 224))  # 填充至224x224
cv2.imwrite("output.jpg", padded_image)  # 保存结果

5. 总结

  • 意义:不变形填充通过保持宽高比填充边缘,解决了图像缩放中的失真问题,同时适配固定尺寸需求。
  • 应用场景:深度学习、图像显示、数据增强等。
  • 优势
    • 避免内容扭曲,提升视觉效果。
    • 统一图像尺寸,兼容模型输入要求。
    • 灵活填充策略(颜色、均值、随机)适应不同需求。

通过这种技术,可以在保持图像内容完整性的同时,满足下游任务对尺寸的严格要求。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值