openCV._imread opencv

openCV._imread opencv         近日,开始学习图像处理,思前想后决定以opencv作为实验基础。遂完成图片读取和显示功能。Imread作为常用的图像读取函数,虽然简单,但是参数的选择非常重要,直接影响到后期处理。同时在调试学习过程中也可以学习到图像处理的知识。1.函数原型Matimread(constString&filename,intflags=IMREAD_COLOR)…

大家好,又见面了,我是你们的朋友全栈君。如果您正在找激活码,请点击查看最新教程,关注关注公众号 “全栈程序员社区” 获取激活教程,可能之前旧版本教程已经失效.最新Idea2022.1教程亲测有效,一键激活。

Jetbrains全系列IDE稳定放心使用

          近日,开始学习图像处理,思前想后决定以opencv作为实验基础。遂完成图片读取和显示功能。Imread作为常用的图像读取函数,虽然简单,但是参数的选择非常重要,直接影响到后期处理。同时在调试学习过程中也可以学习到图像处理的知识。
1. 函数原型

   Mat imread(const String& filename,int flags = IMREAD_COLOR);

    返回Mat对象;

       参数filename: 待打开图片的绝对地址,需要注意的是,并不是所有文件都可以用它打开,它支持的文件如下;函数识别不是依靠文件的后缀名,而是依靠内容的编码格式;

需要注意的是imread读取数据时会重新排列数据。

  •     Windows bitmaps – *.bmp, *.dib (always supported)
  •     JPEG files – *.jpeg, *.jpg, *.jpe (see the Notes section)
  •     JPEG 2000 files – *.jp2 (see the Notes section)
  •     Portable Network Graphics – *.png (see the Notes section)
  •     WebP – *.webp (see the Notes section)
  •     Portable image format – *.pbm, *.pgm, *.ppm *.pxm, *.pnm (always supported)
  •     Sun rasters – *.sr, *.ras (always supported)
  •     TIFF files – *.tiff, *.tif (see the Notes section)
  •     OpenEXR Image files – *.exr (see the Notes section)
  •     Radiance HDR – *.hdr, *.pic (always supported)
  •     Raster and Vector geospatial data supported by Gdal (see the Notes section)

    参数flags:打开的参数,这个非常重要,因为如果设置不合适的话,很容易出现预想之外的效果。它可以指导将原图读取时进行一定的转换。默认值是IMREAD_LOAD_GDAL。因此,如果是想直接处理原图,应该设置为IMREAD_UNCHANED。

openCV._imread opencv

 

2. 通道编码顺序

    通道,与像素深度深度有关。灰度图通常是8比特的像素深度,则通道数为1。如果是彩色图,且为RGB编码,那么一般为24比特的像素深度,通道数为3。而有的彩色图的像素深度是16或者32比特。16比特可能有多种情况:一是压缩的RGB格式,二是YUV的输出。无论何种,都是只有2通道,需要手动解析分离。32比特(windows *.bmp)的像素深度对应的彩色图,则表示的是4通道,RGBA,多出的A表示的是透明度的索引。

    另外读取时需要注意内部像素的编码顺序,这也依赖于imread的flags选项的取值,如果取值决定转成RGB,那么正常的顺序是BGR,排列顺序如下图所示。如果最后imread输出是四通道,多了Alpha通道,那么顺序是RGBA。

    

3, 图像像素通道数据访问

    这部分可以借鉴网上资料,可以分为三种类型。

3.1 动态访问at<typename>(i,j)

    Imread返回的mat类,提供了at模板函数。Image.at<uchar>(i, j);取出i行j列的数据,uchar可以理解为imread返回之后图像的编码类型(如1所述的通道)。如果是三通道,则可以是Vec3b,四通道则是Vec4b。

//CV_LOAD_IMAGE_UNCHANGED如果要取A分量那么flag最好设置成这个值
Mat image = imread("1_firstlai.png", CV_LOAD_IMAGE_UNCHANGED);

for(int i=0;i<image.rows;i++)

{

    for(int j=0;j<image.cols;j++)

    {

        image.at<Vec3b>(i,j)[0]; //B

        image.at<Vec3b>(i,j)[1]; //G

        image.at<Vec3b>(i,j)[2]; //R

       

        image.at<Vec4b>(i,j)[0]; //B

        image.at<Vec4b>(i,j)[1]; //G

        image.at<Vec4b>(i,j)[2]; //R

        image.at<Vec4b>(i,j)[3]; //A

    }

}

 
3.2 指针-更加高效
 

imgage.ptr<uchar>(i)。

int nr=image.rows;

// 将3通道转换为1通道

int nl=image.cols*image.channels();

for(int k=0;k<nr;k++)

{

    // 每一行图像的指针

    const uchar* inData=image.ptr<uchar>(k);

    for(int i=0;i<nl;i++)

    {

        inData[i];

    }

}

    本质就是将每行的3/4通道数据转换为1通道数据访问,因为OpenCV内部存储每一行像素数据以及像素内部通道数据都是连续存储的。但是行与行的数据并不一定是连续存储的,所以不能应用在行与行之间。
3.3 结合isContinuous的指针

    3.2中已经说明了,OpenCV中行与行之间不一定连续存储,也就是有可能连续存储,而且提供了对应的API支持判断是否连续这一现象,也可基于此,再提高访问速度。

int nr=image.rows;

int nc=image.cols*image.channels();

if(image.isContinuous()){

    nc=nc*nr;

    nr=1;

}

for(int i=0;i<nr;i++){

    // 每一行图像的指针

    const uchar* inData=image.ptr<uchar>(i);

    for(int j=0;j<nc;j++){

        inData[j];

    }

}

3.4 安全但低效的迭代器

    3.1-3.3的方法虽然效率高,但是如果操作不小心,容易造成数组越界的Bug。所以opencv提供了一种更安全的访问方法-迭代器。

MatIterator_<Vec3b> it_im, itEnd_im;

it_im    = im.begin<Vec3b>();

itEnd_im = im.end<Vec3b>();

for (; it_im != itEnd_im; it_im++, it_om++){  

    (*it_im)[0] ; //B

    (*it_im)[1] ; //G

    (*it_im)[2] ; //R

}  

———————  
作者:时行居正  
来源:CSDN  
原文:https://blog.csdn.net/firstlai/article/details/70882240  
版权声明:本文为博主原创文章,转载请附上博文链接!

版权声明:本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 举报,一经查实,本站将立刻删除。

发布者:全栈程序员-用户IM,转载请注明出处:https://javaforall.cn/184192.html原文链接:https://javaforall.cn

【正版授权,激活自己账号】: Jetbrains全家桶Ide使用,1年售后保障,每天仅需1毛

【官方授权 正版激活】: 官方授权 正版激活 支持Jetbrains家族下所有IDE 使用个人JB账号...

(0)


相关推荐

  • 新手入门树莓派必做的四件事

    新手入门树莓派必做的四件事随着树莓派在国内的热度越来越高,现在已经有很多人开始接触树莓派了。对于新手,有四件必须完成的事:1、为树莓派更换国内源。2、让Raspbian系统显示中文。3、安装中文输入法。4、调整树莓派的时区时间。不过安装一个合适的系统才是这四件事的前提,众多系统中,Raspbian算比较适合新手的。安装系统如果安装Raspbian系统,可以通过这个链接下载镜像

  • 新东方俞敏洪

    新东方俞敏洪新东方俞敏洪作者:郑志颖http://www.caigou.com.cn/news/20170405133.shtml俞敏洪互联网时代的教育技术一个人在具体环境中接受教育,受什么影响?我看受四个因素的影响:时间因素、空间因素、师资因素和工具因素。传…

  • 你真的了解http,https吗?万字长文带你深入了解http!

    你真的了解http,https吗?万字长文带你深入了解http!HTTP协议定义Web客户端如何从Web服务器请求Web页面,以及服务器如何把Web页面传送给客户端。HTTP协议采用了请求/响应模型。客户端向服务器发送一个请求报文,请求报文包含请求的方法、URL、协议版本、请求头部和请求数据。服务器以一个状态行作为响应,响应的内容包括协议的版本、成功或者错误代码、服务器信息、响应头部和响应数据。

  • 从入门到高级Java书籍推荐

    从入门到高级Java书籍推荐前言不管你是转行来学习Java编程,还是你本来就是计算机专业并且继续在这一领域深耕的。除了,大学专业课程的学习以及工作中的实践之外;业余时间的充电,成了技术人员提升自己的必选之路。有的人选择利用金钱换来时间去报学习班培训,有的人利用自学。那么,自学的方法很多种:阅读书籍资料、网上各种技术论坛博客、视频教程等。个人认为,学习一门技术知识掌握的时间快慢:工作(项目)实战&gt;技术培训&…

  • Java 中是如何获取 IP 属地的[通俗易懂]

    Java 中是如何获取 IP 属地的[通俗易懂]细心的小伙伴可能会发现,抖音新上线了IP属地的功能,小伙伴在发表动态、发表评论以及聊天的时候,都会显示自己的IP属地信息这里有三个名词,分别是X-Forwarded-For:一个HTTP扩展头部,主要是为了让Web服务器获取访问用户的真实IP地址。每个IP地址,每个值通过逗号+空格分开,最左边是最原始客户端的IP地址,中间如果有多层代理,每⼀层代理会将连接它的客户端IP追加在X-Forwarded-For右边。X-Real-IP:一般只记录真实发出请求的客户端IP

    2022年10月21日
  • 推荐60多个CSS GALLERY画廊网站

    推荐60多个CSS GALLERY画廊网站

发表回复

您的电子邮箱地址不会被公开。

关注全栈程序员社区公众号