You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Python图像处理:背景减除、居中、缩放、裁剪、配准问题咨询

Python图像处理实操方案(基于OpenCV)

以下方案均依赖opencv-python和numpy库,提前通过pip安装即可使用。


1. 单目标(苹果)自动居中

每张图仅含单个苹果时,不需要复杂分割模型,通过质心检测+平移变换即可实现居中,比固定方向裁剪的鲁棒性更强,不会因为苹果位置特殊丢失边缘内容:

  • 先通过OTSU自适应阈值分割出苹果的二值mask
  • 通过图像矩计算苹果的质心坐标
  • 计算质心与图像画布中心的偏移量,构造平移矩阵做仿射变换,空缺区域填充背景色
import cv2
import numpy as np

def center_apple(img, bg_value=(255,255,255)):
    h, w = img.shape[:2]
    canvas_center_x, canvas_center_y = w//2, h//2
    # 生成苹果分割mask
    gray = cv2.cvtColor(img, cv2.COLOR_BGR2GRAY)
    blur = cv2.GaussianBlur(gray, (5,5), 0)
    _, mask = cv2.threshold(blur, 0, 255, cv2.THRESH_BINARY_INV + cv2.THRESH_OTSU)
    # 计算苹果质心
    M = cv2.moments(mask)
    if M["m00"] == 0:
        return img
    apple_cx = int(M["m10"] / M["m00"])
    apple_cy = int(M["m01"] / M["m00"])
    # 平移对齐中心
    dx = canvas_center_x - apple_cx
    dy = canvas_center_y - apple_cy
    trans_mat = np.float32([[1,0,dx],[0,1,dy]])
    centered_img = cv2.warpAffine(img, trans_mat, (w,h), borderValue=bg_value)
    return centered_img

如果要走纯裁剪逻辑,只需要根据质心位置计算四边裁剪量即可:苹果在左下角时,右侧、上侧的裁剪宽度更大,左、下侧裁剪宽度更小,保证裁剪后的图像中心刚好落在苹果质心上。


2. 多尺寸图像统一调整

根据是否需要保留图像原始比例选对应方案:

  • 不需要保留比例:直接调用cv2.resize(img, (target_w, target_h))即可,缺点是目标可能被拉伸变形
  • 需要保留比例:采用letterbox补边逻辑,等比例缩放后将图像贴在统一尺寸画布的中心,空缺区域填充背景色,无变形
def resize_with_padding(img, target_size=(512,512), bg_value=(255,255,255)):
    h, w = img.shape[:2]
    target_w, target_h = target_size
    scale = min(target_w/w, target_h/h)
    new_w, new_h = int(w*scale), int(h*scale)
    resized_img = cv2.resize(img, (new_w, new_h))
    # 生成画布并贴图
    canvas = np.full((target_h, target_w, 3), bg_value, dtype=np.uint8)
    paste_x = (target_w - new_w) // 2
    paste_y = (target_h - new_h) // 2
    canvas[paste_y:paste_y+new_h, paste_x:paste_x+new_w] = resized_img
    return canvas

3. 固定中心的外围裁剪缩放

该操作不会改变图像中心位置,仅裁掉外围冗余区域后缩放到目标尺寸,适合已经完成目标居中的图像预处理:

  • 先以图像中心为基准,裁剪出和目标尺寸宽高比一致的最大中心区域
  • 将裁剪出的区域直接缩放到目标尺寸即可
def center_crop_and_resize(img, target_size=(512,512)):
    h, w = img.shape[:2]
    target_w, target_h = target_size
    target_ratio = target_w / target_h
    img_ratio = w / h
    # 按比例裁中心区域
    if img_ratio > target_ratio:
        new_w = int(h * target_ratio)
        x_start = (w - new_w) // 2
        cropped = img[:, x_start:x_start+new_w]
    else:
        new_h = int(w / target_ratio)
        y_start = (h - new_h) // 2
        cropped = img[y_start:y_start+new_h, :]
    # 缩放到目标尺寸
    final_img = cv2.resize(cropped, target_size)
    return final_img

注意:该操作会丢弃外围图像内容,如果目标没有提前居中,可能裁掉部分目标主体。


4. 微小偏移图像对齐(配准)用于差分检测

间隔固定时间拍摄的图像仅存在刚性位移(平移、轻微旋转,无明显形变),用OpenCV自带的ECC(增强相关系数)算法即可完成高精度对齐,对齐后再做差分就不会因为偏移产生大量误检:

def align_to_ref(ref_img, moving_img):
    ref_gray = cv2.cvtColor(ref_img, cv2.COLOR_BGR2GRAY)
    moving_gray = cv2.cvtColor(moving_img, cv2.COLOR_BGR2GRAY)
    # 初始化刚性变换矩阵
    warp_mat = np.eye(2, 3, dtype=np.float32)
    # 迭代终止条件
    stop_criteria = (cv2.TERM_CRITERIA_EPS | cv2.TERM_CRITERIA_COUNT, 1000, 1e-8)
    # 计算最优变换参数
    _, warp_mat = cv2.findTransformECC(ref_gray, moving_gray, warp_mat, cv2.MOTION_EUCLIDEAN, stop_criteria)
    h, w = ref_img.shape[:2]
    aligned_img = cv2.warpAffine(moving_img, warp_mat, (w,h), flags=cv2.INTER_LINEAR + cv2.WARP_INVERSE_MAP)
    return aligned_img

# 差分检测调用示例
# ref_frame = cv2.imread("first_shot.jpg")
# next_frame = cv2.imread("5min_later.jpg")
# aligned_frame = align_to_ref(ref_frame, next_frame)
# # 计算差分图
# diff = cv2.absdiff(ref_frame, aligned_frame)
# diff_gray = cv2.cvtColor(diff, cv2.COLOR_BGR2GRAY)
# # 阈值过滤噪声,得到真实变化区域
# _, change_mask = cv2.threshold(diff_gray, 25, 255, cv2.THRESH_BINARY)

如果图像位移极小、没有旋转,也可以用相位相关算法直接计算x/y方向的平移量,对齐速度更快。


内容的提问来源于stack exchange,提问作者김수환

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.02 21:21:36