java简单实现八叉树图像处理代码示例

  

一晃工作有段时间了,第一次写博客,有点不知道怎么写,大家将就着看吧,说的有什么不正确的也请大家指正。

  

最近工作中用到了一个图像压缩的功能。找了一些工具,没有太好的选择。最后选了一个叫jdeli的,奈何效率又成了问题。我迫于无奈就只能研究了下它的源码,却发现自己对它的一个减色量化算法起了兴趣,可是尴尬的自己完全不明白它写的什么,就起了一个自己实现一个量化颜色算法的念头。

  

自己找了一些资料,找到三个比较常用的颜色处理算法:

  

流行色算法:

  

具体的算法就是,先对一个图像的所有颜色出现的次数进行统计,选举出出现次数最多的256个颜色作为图片的调色板的颜色,然后再次遍历图片的所有像素,对每个像素找出调色板中的最接近的颜色(这里我用的是方差的方式),写回到图片中。这个算法的实现比较简单,但是失真比较严重,图像中一些出现频率较低,但对人眼的视觉效挺明显的信息将丢失。比如,图像中存在的高亮度斑点,由于出现的次数少,很可能不能被算法选中,将被丢失。

  

中位切分算法:

  

这个算法我没有研究,想要了解的同学,可以看下这篇文章,里面有三种算法的介绍。

  

八叉树   

这个算法就是我最后选用的算法,它的主要思想就是把图像的RGB颜色值转成二进制分布到八叉树中,例如:(173234144)

  

转成二进制就是(10101101、10101101和10101101),将R, G, B的第一位取出来组成(111),作为根节点的子节点,其111年中作为根子节点数组的索引,以此类推,一直到最后一位,然后在叶子节点上存放这个颜色的分量值以及其出现的次数。具体看图。

  

癹ava简单实现八叉树图像处理代码示例"

  

其中我比较疑惑的有一个处理就是叶子节点的合并策略,这儿我用的最笨的一个方法,就是找到层次最深的节点,然后合,并有点简单粗暴,有别的比较好的方法,也请大家给我留的言。图片太大上传不了的了,直接上代码了,代码没有重构,大家凑合看吧。

        包com.gys.pngquant.octree;   进口java.util.ArrayList;   进口java.util.HashMap;   进口并不知道;   进口java.util.Map;/* *   *   *   * @ClassName类名:节点   * @Description功能说明:   * & lt; p>   *八叉树实现   * & lt;/p>   *   * 2015-12-16 guoys创建该类功能。   *   **********************************************************   * & lt;/p>   */公共类节点{   私人int深度=0;//为0时为根节点   私人父节点;   私人节点[]儿童=新节点[8];   私人布尔isLeaf=false;   私人int rNum=0;   私人int gNum=0;   私人int bNum=0;   私人int piexls=0;   私人Map<整数,List比;levelMapping;//存放层次和节点的关系   公共int getRGBValue () {   int r=Num/this.piexls;   int g=Num/this.piexls;   int b=Num/this.piexls;   返回(r & lt; & lt;16 | g & lt; & lt;8 | b);   }   公共Map<整数,List比;getLevelMapping () {   返回levelMapping;   }   公共空间afterSetParam () {   如果(this.getParent()==零,,this.depth==0) {   levelMapping=new HashMap<整数,List在();   for (int i=1;我& lt;=8;我+ +){   levelMapping。把(我,新的ArrayList ());   }   }   }   公共int getrNum () {   返回rNum;   }   公共空间setrNum (int rNum) {   如果(! isLeaf) {   抛出UnsupportedOperationException()方式;   }   这一点。rNum=rNum;   }   公共int getgNum () {   返回gNum;   }   公共空间setgNum (int gNum) {   如果(! isLeaf) {   抛出UnsupportedOperationException()方式;   }   这一点。gNum=gNum;   }   公共int getbNum () {   返回bNum;   }   公共空间setbNum (int bNum) {   如果(! isLeaf) {   抛出UnsupportedOperationException()方式;   }   这一点。bNum=bNum;   }   公共int getPiexls () {   返回piexls;   }   公共空间setPiexls (int piexls) {   如果(! isLeaf) {   抛出UnsupportedOperationException()方式;   }   这一点。piexls=piexls;   }   公共int getDepth () {   返回深度;   }//返回节点原有的子节点数量   公共int mergerLeafNode () {   如果(this.isLeaf) {   返回1;   }   this.setLeaf(真正的);   int rNum=0;   int gNum=0;   int bNum=0;   int像素=0;   int i=0;   (节点的孩子:this.children) {   如果孩子==null) {   继续;   }   rNum +=child.getrNum ();   gNum +=child.getgNum ();   bNum +=child.getbNum ();   像素+=child.getPiexls ();   我+=1;   }   this.setrNum (rNum);   this.setgNum (gNum);   this.setbNum (bNum);   this.setPiexls(像素);   这一点。孩子=零;   返回我;   }//获取最深层次的节点   公共节点getDepestNode () {   for (int i=7;我在;0;我(){   List

java简单实现八叉树图像处理代码示例