使用Java开发OpenCV3程序-3.OpenCV的组件结构以及java版本的数据结构

OpenCV组件结构

  关于OpenCV的组件结构“浅墨”大神给出了详细的解释,详细的参照:一览众山小:OpenCV 2.4.8 or OpenCV 2.4.9组件结构全解析 但在OpenCV3.1中还是有些变化的,在opencv/build/include/opencv2目录下有OpenCV的所有模块,

一共有这么多模块,在浅墨的文章中也做了详细的介绍,有些模块已经没有了。然后再看看java中所包含的模块,可以从opencv.jar中看到所实现的模块:

明显看到跟C++版本的少了很多模块,但是基本的功能模块都已经有了,官方应该也在不断晚上java版本的接口,不久的将来也应该会拥有跟C++版本一模一样的功能吧。可以到各个模块中查看所实现的方法,一般的方法中都有注释,而且方法的名字都是跟C++中是一样的。

  我们知道一幅图片都是有不同的像素点组成的,每个像素点的值代表了一个颜色,比如一副灰度图像,从0(黑色)到255(白色)来代表颜色的深浅。而通常一幅彩色图像又是由红绿蓝三种颜色组成,俗称RGB图像。更多关于图像与颜色可以参考数字图像处理方面的书籍,这是介绍OpenCV是如何来表示不同的图像的。在core->CvType中定义了很多关于图像类型的常量,基本结构是:

  CV_<位数>{U|S|F}C(<通道数>)     位数=8|16|32|64   通道数=1|2|3|4  最多只有四通道。  下面以一通道的来做详细的说明。

  • CV_8UC1 8位无符号整数从0到255
  • CV_8SC1 8位有符号整数从-128到127
  • CV_16UC1 16位无符号整数从0到65536
  • CV_16SC1 16位有符号整数从-32768到32767
  • CV_32SC1 32位有符号整数从-2^(32-1)到2^(32-1)-1
  • CV_32FC1 32位有符号小数
  • CV_64FC1 64位有符号小数
你可以使用这样的方式来创建一幅图片:

Mat image = new Mat(new Size(3,4), CvType.CV_8UC3, new Scalar(new double[]{128,3,4}));

  Mat有很多中构造方法,这里只是其中一种,这样构造的mat对象含义是宽度为3个像素,高度为4个像素,8位无符号三通道图像,第一通道也就是Red全为128,第二通道Green全为3,第三通道Blue全是4,我们可以使用如下的代码打印出这个对象的信息以及每个像素点的数据。

        Mat image = new Mat(new Size(3, 4), CvType.CV_8UC3, new Scalar(new double[]{128, 3, 4}));
        System.out.println(image + " width=" + image.width() + " height=" + image.height());
        System.out.println(image.dump());

直接使用Mat对象的toString()方法,将会打印出mat对象的基本信息,dump()返回每个像素点的值,注意当像素宽高太大时,可能耗时比较长。输出结果:

Mat [ 4*3*CV_8UC3, isCont=true, isSubmat=false, nativeObj=0x50aaf0, dataAddr=0x4dce00 ] width=3 height=4
[128,   3,   4, 128,   3,   4, 128,   3,   4;
 128,   3,   4, 128,   3,   4, 128,   3,   4;
 128,   3,   4, 128,   3,   4, 128,   3,   4;
 128,   3,   4, 128,   3,   4, 128,   3,   4]

由于图像太小,显示出来也是特别小,基本看不出来,可以把宽高设置大一些然后显示,就是一片深蓝色,也就是red=128,green=3,blue=4的颜色。

一些需要注意的点:

  java中没有无符号这个说法,所有的基本数据类型都是有符号的,比如对于CV_8UC1来说,需要表示的像素是从0到255,在C++中只需要一个byte就够了,但是java中确不能用一个字节来表示0到255,所以是只能向上类型转换了。我们先来看一段代码:

        Mat image = new Mat(new Size(3, 4), CvType.CV_8UC1, new Scalar(new double[]{234}));
        image.put(1, 2, new byte[]{123});
        System.out.println(image);
        System.out.println(image.dump());

        image.put(1, 2, new byte[]{200 - 256});
        System.out.println(image.dump());

  这段代码先创建了一个3*4的8位单通道无符号的图像,每个像素点都是234,然后将[1,2]这个位置(注意从[0,0]坐标点开始计数)值置为123,然后打印出来像素,没问题,123<127所以可以put成功,但是如果我们想改一个大于127的值呢,byte数据会直接报错,编译都无法通过,那是不是就无法创建一个大于127的值呢,当然不是,将大于127的值减去一个256,比如现在我想设置成200,怎么做呢,直接用200-256,也就是存一个-56,然后再打印出来看看是不是可以。结果当然是可以的,200已经设置成功了。那如果是一个CV_8SC1的图像呢,该是多少直接设置成多少就可以了。为什么能打印出200呢,不是byte值得吗?不妨看看image.get(1,2)这个方法,这个方法返回了一个double[]类型,当时能保存200了,而dump返回的是String,在内部已经将-56转成了200的字符串.

  所以对于获得一幅图像的像素点的时候不用考虑太多,但是如果你要设置某个像素点,并且这个像素点的数据类型或是位宽小于你要设置的值得位宽时,就得注意了,不过也有更安全的做法,那就是全都使用double设置,在内部会自动转换。后面会看到在java版本的OpenCV的方法中很多地方都是使用的是double,这个确实是浪费了很多内存,很多时候我们处理的都是8位无符号的3通道彩色图像,映射到java程序中,如果要把这个图像的数据dump过来,那就得8倍的内存来保存(C++中一个字节就够但java就需要用double表示,double占了8位)。

  下一遍开始就正式要开始介绍使用OpenCV来处理图像了。

时间: 2024-10-01 02:52:15

使用Java开发OpenCV3程序-3.OpenCV的组件结构以及java版本的数据结构的相关文章

Android学习笔记(43):Java开发SQLite程序

正如前面一文说的,SQLite多用于嵌入式开发中,但有时为了更方便的编辑数据库文件,我们也常常需要开发在电脑上运行的SQLite程序.这种情况是经常发生的,比如在我们需要把一大批的txt文件中的数据插入到一个数据库中的时候. 还好这是很简单的,所以本文我们来学习如何用Java开发SQLite程序. (1)准备工作 下载sqlite-jdbc-版本号.jar文件,放到jre\lib\ext文件夹.如我的路径是C:\Program Files\Java\jre1.8.0_77\lib\ext. (2

底层战详解使用Java开发Spark程序(DT大数据梦工厂)

Scala开发Spark很多,为什么还要用Java开发原因:1.一般Spark作为数据处理引擎,一般会跟IT其它系统配合,现在业界里面处于霸主地位的是Java,有利于团队的组建,易于移交:2.Scala学习角度讲,比Java难.找Scala的高手比Java难,项目的维护和二次开发比较困难:3.很多人员有Java的基础,确保对Scala不是很熟悉的人可以编写课程中的案例预测:2016年Spark取代Map Reduce,拯救HadoopHadoop+Spark = A winning combat

java开发GUI程序一般步骤:

开发GUI程序一般步骤: 1. 引包 import java.awt.*; import javax.swing.*; 2. 继承JFrame public class Demo3 extends JFrame {} 3. 定义需要的组件 //3.定义组件 JButton jb1,jb2,jb3,jb4,jb5; int size=9; JButton jbs[]=new JButton[size]; //先分配初始空间 4. 创建组件 //4.创建组件 jb1=new JButton("中部&

Java全栈程序员之02:Ubuntu下Java环境安装、配置、测试

在上文讲完之后,我们手里的ubuntu只能算是一个上网机,什么也干不了,本篇我们将折腾它为开发机. 这里,我们这里假定你对linux体系是初级选手,所以本篇会讲的啰嗦一点,高手就出门左转吧. 1.安装 首先我们确定下我们安装的Ubuntu系统是否已经安装了java环境. 进入终端,敲入命令su,进入root模式(当然也可以省掉这一步),敲入命令java -version.如果看到这个界面,说明尚未安装Java环境, Ps:我们的课程中曾经讲过如何删除一个老的jdk,这里就略过不讲了. 继而,让我

搭建一套Java开发环境以及使用eclipse从头一步步创建java项目

一.java 开发环境的搭建 在windows 环境下怎么配置环境. 1.首先安装JDK java的sdk简称JDK ,去其官方网站下载JDK. https://www.oracle.com/technetwork/java/javase/downloads/jdk8-downloads-2133151.html 2.环境变量配置 运行下载的  jdk-7u13-windows-i586.exe 配置.检查JAVA_HOME,PATH, CLASSPATH 三个属性. windows10,右键

WebService应用--使用java开发WebService程序

使用Eclipse开发第一个WebService程序,本示例采用的工具为Spring-Tool-Suite,和Eclipse没有本质的区别,开发环境jdk1.7 一.开发步骤: 1.新建名为WebService项目 新建HelloService类,放在com.test.webservice包下 下面进行服务端程序的编写: 1 package com.test.webservice; 2 import javax.jws.WebService; 3 import javax.xml.ws.Endp

Java开发Spark程序

pom.xml <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> <mo

java开发GUI程序,用maven搭建环境

一.eclipse安装好maven插件之后,用maven的archetype创建一个OSGI项目,搭建好项目骨架. 二.可执行jar文件分为两种,一种是可通过命令行java -jar xxx.jar 可以直接运行的jar文件,一种是工其他jar文件调用的jar文件.第一种jar文件的META-INF文件夹下的manifest.MF文件含有Main-Class值,第二种jar文件则不包含.第一种的jar文件可以直接运行的原因是,其可以直接调用到其所依赖依赖的jar包,第一种方式是直接在manife

Java开发桌面程序学习(四)——常用应用布局模板和简单分析

布局 前言 刚开始的时候,不知道使用什么布局,发现SceneBuilder其实有8.5版本的,里面就是有提供一个简单的桌面程序模板,8.5可以去官网下载,不过网速好像有点慢,慢慢等吧,官网下载地址 布局分析 外层是一个VBox,然后使用MenuBar,MenuBar的宽度就会自动和VBox的宽度保持一致(之前我使用的是FlowPane,弄了半天都不能自动适应宽度). MenuBar中有很多常用的MenuItem选项,我们可以根据自己的选择删除,并修改文字 中间的空白面板就是一个AnchorPan