opencv学习之遍历图像

opencv中遍历图像是个问题,因为opencv有时候是要求速度的,特别是目标跟踪的时候。在这里大概可以分。。。。。。就4种吧。

测试图片是100×100的rgb图像,从srcImg图像拷贝到dstImg图像,使用了三种方法,iterator、at、指针ptr方法。依次速度加快。
我的机器上iterator方法跑了个50+ms,at方法跑了3ms,二维方法跑了0ms,一维数组方法也是0ms,大家看相对就行了,以后想快点的话,iterator就不要考虑了,直接用指针方法就行了。

其中二维数组和一维数组方法分别是对每一行看作一个一维数组,和对整幅图像看作一个一维数组。
但是注意一维数组方法需要图像是iscontinuous()的,每次遍历之前都需要判断是不是连续的,如果一定想要用一维数组方法,可以将图像使用create方法创建,这样就可以保证图像是iscontinuous()的了。
下边是源码测试。

#include <opencv2/opencv.hpp>
#include <iostream>
#include <ctime>
using namespace cv;
using namespace std;
int main()
{
    Mat srcImg=imread("F:\\0.jpg");
    Mat dstImg(srcImg.size(),srcImg.type());
    int start=clock();
    for(int i=0;i<srcImg.rows;i++)
    {
        for(int j=0;j<srcImg.cols;j++)
        {
            dstImg.at<Vec3b>(i,j)=srcImg.at<Vec3b>(i,j);
        }
    }
    int end=clock();
    cout<<"at 方法:"<<end-start<<endl;
    imshow("dst",dstImg);
    waitKey(0);

    Mat ptrSrcImg=imread("F:\\0.jpg");
    Mat ptrDstImg(ptrSrcImg.size(),ptrSrcImg.type());
    int ptrStart=clock();
    Vec3b* srcData;
    Vec3b* dstData;
    for(int i=0;i<ptrSrcImg.rows;i++)
    {
        srcData=ptrSrcImg.ptr<Vec3b>(i);
        dstData=ptrDstImg.ptr<Vec3b>(i);
        for(int j=0;j<ptrSrcImg.cols;j++)
        {
            dstData[j]=srcData[j];
        }
    }
    int ptrEnd=clock();
    cout<<"二维数组 方法:"<<ptrEnd-ptrStart<<endl;
    imshow("ptrdstImg",ptrDstImg);
    waitKey(0);

    Mat iteSrcImg=imread("F:\\0.jpg");
    Mat iteDstImg(iteSrcImg.size(),iteSrcImg.type());
    int iteStart=clock();
    MatIterator_<Vec3b> itSrc=iteSrcImg.begin<Vec3b>();
    MatIterator_<Vec3b> itDst=iteDstImg.begin<Vec3b>();
    for(;itSrc!=iteSrcImg.end<Vec3b>();itSrc++,itDst++)\
    {
        itDst[0]=itSrc[0];
        itDst[1]=itSrc[1];
        itDst[2]=itSrc[2];
    }
    int iteEnd=clock();
    cout<<"iterator 方法: "<<iteEnd-iteStart<<endl;
    imshow("iteDstImg",iteDstImg);
    waitKey(0);

    Mat secPtrSrcImg=imread("F:\\0.jpg");
    Mat secPtrDstImg(secPtrSrcImg.size(),secPtrSrcImg.type());
    int secPtrStart=clock();
    if(secPtrSrcImg.isContinuous())
    {
        Vec3b* secDstData=secPtrDstImg.ptr<Vec3b>(0);
        Vec3b* secSrcData=secPtrSrcImg.ptr<Vec3b>(0);
        for(int i=0;i<secPtrDstImg.rows*secPtrDstImg.cols;i++)
        {
            secDstData[i]=secSrcData[i];
        }
    }
    int secPtrEnd=clock();
    cout<<"一维数组方法:"<<secPtrEnd-secPtrStart<<endl;
    imshow("secPtrImg",secPtrDstImg);
    waitKey(0);
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值