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

通过Pybind11传递C++ cv::Mat到Python YOLO触发std::bad_alloc错误

解决C++ cv::Mat传递给Ultralytics YOLO触发std::bad_alloc的问题

以下是针对该问题的常见原因及对应解决方法:

1. 通道顺序不匹配

C++ cv::imread 默认读取BGR格式图像,但Ultralytics YOLO的Python接口处理时,会自动将cv2.imread的BGR输入转为RGB;而C++传递的Mat直接进入推理时,缺少这个转换步骤,导致模型内部内存计算错误。

修复代码:

cv::Mat img = cv::imread("your_image.jpg");
cv::cvtColor(img, img, cv::COLOR_BGR2RGB); // 转为YOLO期望的RGB格式

2. 内存连续性问题

Python的numpy数组是内存连续的,而C++的cv::Mat可能因读取或后续操作导致内存不连续,步长与numpy的预期不符,YOLO处理时会错误计算内存需求,触发std::bad_alloc。

修复代码:

if (!img.isContinuous()) {
    img = img.clone(); // 克隆生成内存连续的Mat
}

3. Pybind11转换错误

若未正确使用Pybind11的OpenCV转换器,或返回的Mat生命周期管理不当,会导致Python端拿到无效内存地址。

修复要点:

  • 必须包含头文件 <pybind11/opencv.h>,确保cv::Mat与numpy数组的自动转换
  • 绑定函数返回cv::Mat值(而非引用/指针),让Pybind11处理内存:
#include <pybind11/pybind11.h>
#include <pybind11/opencv.h>

namespace py = pybind11;

py::Mat load_image(const std::string& path) {
    cv::Mat img = cv::imread(path);
    cv::cvtColor(img, img, cv::COLOR_BGR2RGB);
    if (!img.isContinuous()) img = img.clone();
    return img;
}

PYBIND11_MODULE(yolo_cpp_bind, m) {
    m.def("load_image", &load_image, "Load image in C++ for YOLO inference");
}

4. 数据类型不匹配

YOLO默认要求输入为8位无符号三通道图像(CV_8UC3),若C++读取的Mat是灰度图、16位深度等格式,会触发内存分配错误。

修复代码:

// 强制读取为彩色图,再转为CV_8UC3格式
cv::Mat img = cv::imread(path, cv::IMREAD_COLOR);
img.convertTo(img, CV_8UC3);

内容的提问来源于stack exchange,提问作者shipeng zeng

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.15 17:35:17