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

OpenCV 2.x迁移至3.x:cvGetMat函数替代方案咨询

替代OpenCV 3.x中已移除的cvGetMat()函数

Hey, I see you're hitting this error:

‘cvGetMat’ was not declared in this scope CvMat srcstub, *src = cvGetMat( srcarr, &srcstub ); ^~~~~~~~

That's totally expected—cvGetMat() got dropped from OpenCV 3.x's C API. But there are two great workarounds, depending on whether you can shift to the recommended C++ interface or need to keep your code in pure C.

推荐方案:切换到C++接口的cv::cvarrToMat()

If you're open to migrating to the C++ API (which is the way to go since OpenCV has been prioritizing it for years), cv::cvarrToMat() does exactly what cvGetMat() used to do, but without the hassle of stub variables. It converts old C-style arrays (IplImage* or CvMat*) directly to cv::Mat objects seamlessly.

Here's how to update your code snippet:

#include <opencv2/opencv.hpp>

void cvCanny3(const void* srcarr, void* dstarr, void* dxarr, void* dyarr, int aperture_size) {
    // Convert C-style input arrays to cv::Mat objects
    cv::Mat src = cv::cvarrToMat(static_cast<const CvArr*>(srcarr));
    cv::Mat dst = cv::cvarrToMat(static_cast<CvArr*>(dstarr));
    cv::Mat dx = cv::cvarrToMat(static_cast<CvArr*>(dxarr));
    cv::Mat dy = cv::cvarrToMat(static_cast<CvArr*>(dyarr));
    
    // Your existing logic can now use these cv::Mat instances—you can even switch to C++ versions of OpenCV functions here for better long-term support
    // ...
}

纯C代码兼容方案

If you absolutely need to retain pure C code, you'll have to replicate what cvGetMat() did manually by checking the input type and creating a CvMat header for image inputs.

Here's the adjusted code:

#include <opencv2/imgproc/imgproc_c.h>

void cvCanny3(const void* srcarr, void* dstarr, void* dxarr, void* dyarr, int aperture_size) {
    CvMat* src;
    // Check if input is already a CvMat
    if (CV_IS_MAT(srcarr)) {
        src = (CvMat*)srcarr;
    } 
    // Handle IplImage inputs by creating a CvMat header pointing to the image data
    else if (CV_IS_IMAGE(srcarr)) {
        IplImage* src_img = (IplImage*)srcarr;
        src = cvCreateMatHeader(src_img->height, src_img->width, CV_MAKETYPE(src_img->depth, src_img->nChannels));
        cvSetData(src, src_img->imageData, src_img->widthStep);
    } 
    // Handle invalid input types
    else {
        return;
    }

    // Repeat the same logic for dst, dx, and dy
    CvMat* dst;
    if (CV_IS_MAT(dstarr)) {
        dst = (CvMat*)dstarr;
    } else if (CV_IS_IMAGE(dstarr)) {
        IplImage* dst_img = (IplImage*)dstarr;
        dst = cvCreateMatHeader(dst_img->height, dst_img->width, CV_MAKETYPE(dst_img->depth, dst_img->nChannels));
        cvSetData(dst, dst_img->imageData, dst_img->widthStep);
    } else {
        return;
    }

    // ... Apply the same handling for dx and dy ...

    // Note: You don't need to free the created CvMat headers—they just reference the original image's data, so no memory leaks here
    // Proceed with your existing C-style OpenCV logic
    // ...
}

Key Notes:

  • Prioritize the C++ approach: OpenCV's C API is deprecated and will likely be completely removed in future versions, so migrating to C++ will save you from more compatibility issues down the line.
  • The error you're seeing is just OpenCV telling you that cvGetMat() no longer exists in 3.x+—the workarounds above replicate its original functionality without relying on the removed function.

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.29 07:10:23