数字图像点运算尽 (直方图均衡和分段线性拉伸)

zsm  http://i.cnblogs.com/EditPosts.aspx?opt=1

摘要

人类所收获的音讯大约70%源于于图像,数字图像处理是计算机对采样量化的图像进行删除噪声、增强、复原、分割、提前特征等拍卖的不二法门与技能,它对一个体的数字代表施加相同密密麻麻之操作,以得所幸之结果。这种技术以航空航天、生物医学、通信工程、军事、文化、电子商务等地方使广泛。本实验依据课堂所学的有关数字图像点运算的知实现对数字图像的灰度直方图均衡处理分段线性拉伸处理

 

关键词

数字图像  点运算  灰度直方图  直方图均衡  分段线性拉伸

平等、 任务说明

于是Java编程语言实现一个带GUI的数字图像处理程序,实现读出数字图像并拓展灰度直方图均衡处理及分段线性拉伸处理的作用。

内需专注的凡,在本程序中,对于分段线性拉伸处理,程序中会优先根据来自图像的灰度直方图找来集中分布区间(像从个数的同占图像总像素个数85%之上之间隔中长度最差的间隔),然后被用户输入一个而拉扯伸到之区间,再拓展分段线性拉伸。拉伸前后灰度范围都沉默认为
[0,255]。

亚、 算法原理

(一)直方图均衡

1、            背景意义

直方图反映的是一律幅图像的灰度级与出新这种灰度级概率之间涉及的图纸。直方图均衡的目的是若有灰度级出现的相对概率一样,此时图像的熵最要命,图像包含的消息太可怜。经过直方图均衡处理后,图像的指向比度会增高,特别是于背景或前景还太亮或太暗的图像非常有效。例如,其可以带动X光图像被再好之骨骼布局显示和曝光过度或曝光不足照片遭还好之底细。

直方图均衡的首要优势是其是一个相当直观的艺并且是可逆操作,如果已经知道均衡化函数,那么尽管得回复老之直方图,并且计算量也未深。这种方式的一个短是她对处理的数未加以选择,它恐怕会见多背景噪声的对比度并且降低中信号的针对性比度。

 

2、            主干算法

若灰度级概率分布函数为 ,则这直方图均衡的变换函数 s=T[r]
应该满足如下条件:

 

(a)       T[r]啊单值单调递增函数

(b)       0<T[r]<1,保证易后像素灰度级仍当兴范围外

是因为易原理可求得

虽然原灰度值 r 经变换后对应的初灰度值为

 

3、            扩张算法

上述基本算法是对此灰度级连续的事态而言的,而于电脑中图像的灰度级是离散的,实际上和连续情况相近,我们好博得离散情况下之变换函数:

使离散情况下同步发出L个灰度级,第k独灰度级出现的像素个数为,图像的总像素个数为N,则第k单灰度级出现的概率也:

 

就此均衡化的变换函数为:

 

虽原灰度值r对应之初灰度值为

因此通过更换原图像每个像素的灰度值就可实现直方图均衡处理。

 

(二)分段线性拉伸

1、            背景意义

一般成像系统就持有一定之亮度响应范围,亮度的绝酷价值和最小值的比较称为对比度。由于成像系统的限量,常常出现对比度不足之题材,使人口眼观看图像时的视觉效果较差,可以行使灰度变换(灰度修正)方法提高图像的对准比度,增强图像。常用之灰度修正方法有:

(1)       线性变换

(2)       分段线性变换

(3)       非线性变换,如指数变换、对数变换等

此以的凡 分线性变换

2、            骨干算法

为突出感兴趣的对象或灰度区间,相对抑制不感兴趣的灰度区间,可以运用分段线性变换。常因此三段线性变换方法。

设原灰度直方图的灰度级的分布范围为[0,],集中分布于[a,b],又设变换后的直方图灰度级的分布范围吗[0,],集中分布在[c,d],则转移公式如下:

对 :

对 :

对 :

3、            壮大算法

每当按实验中,和还算255,而原本灰度级的汇总分布范围 [a,b]
是通过序算出来的,即于本图像的灰度直方图备受追寻有一个连接灰度区间
[a,b] ,这个间隔满足个别个原则:

 

(1)       在斯灰度级区间内的像素个数和占总像素个数的85%上述

(2)       此区间是满足(1)的间隔中间隔长度最缺乏的

 

流动:上述比例85%是于先后中默认的,其实该做成能被用户自己输入一个比例,然后程序找有之比重下灰度级的集中分布区间,但鉴于时日有限,程序中只默认为85%,没有落实为用户输入比例之功力。

老三、 算法实现

功能函数:功能说明,输入参数说明,输出参数说明,算法流程(代码或伪代码,注释)

(一)         使用语言

本程序采用Java语言编写,开发平台为Eclipse (Version: Juno)

(二)         编译环境

java version “1.7.0_25”

Java(TM) SE Runtime Environment (build 1.7.0_25-b17)

(三)         功能函数

1、private BufferedImage getGrayPicture(BufferedImage originalImage)

(1)   功用说明:此函数获得输入图像的灰度图像,以及对应之灰度分布

(2)   输入参数说明:originalImage为输入的图像,类型为BufferedImage

(3)  
出口参数说明:调用此函数后收获输入图像对应之灰度图像,并拿个灰度级的像素个数存入全局数组huidunum[]着,供后面处理的用

(4)   好不容易法流程:

遍历每个像素——>

抱该像素RGB值——>

获得R、G、B分量——>

抱灰度值——>

坐灰度值为新R、G、B分量,得到新RGB值——>

新像素

* *

    // 获得图像的灰度图,并获取该图像个灰度级的诸如素个数 huidunum[]

    private BufferedImage getGrayPicture(BufferedImage
originalImage) {

        int rgb, gray, alph, red, green, blue;

        int imgwidth = originalImage.getWidth();

        int imgheight = originalImage.getHeight();

        BufferedImage
huiduimg = new BufferedImage(imgwidth, imgheight,

                originalImage.getType());//
不在原图像上改动,而是创建同大小的相同张图

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

            huidunum[i] = 0; //
灰度分布初始化为0,即每灰度值像从个数初始化为0

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

            for (int j = 0; j < imgheight; j++) {//
遍历图像所以像素

                rgb = originalImage.getRGB(i, j);// 获得该像素的rgb值,为一个4字节之平头,从大至小各字节值

                                                    // 分别代表

                                                    // 透明度appha、red、green、blue

 

                alph = rgb >> 24; // 得到appha的值

                red = (rgb & 0xff0000) >> 16;// 得到red值

                green = (rgb & 0xff00) >> 8;// 得到green值

                blue = (rgb & 0xff);// 得到blue值

 

                gray = (int) (red * 299 + green * 587 + blue *
114) / 1000;// 根据公式由rgb三分量值得到灰度值gray

 

                huidunum[gray]++;// 该灰度值像从个数加相同

 

                rgb = (alph << 24) | (gray << 16) | (gray
<< 8) | gray;// 由灰度值转rgb值,三重量都是gray值

                huiduimg.setRGB(i, j, rgb);// 新rgb值

            }

        }

        return huiduimg;

}

* *

2、private BufferedImage hisEqual(BufferedImage originalImage)

(1)    力量说明:此函数实现直方图均衡化的功效

(2)    输入参数说明:originalImage为读入的图像

(3)    出口参数说明:获得对应之通过直方图均衡处理后的图像

(4)    算是法流程:

遍历每个灰度值的诸如素个数huidunum[]——>

获灰度值范围[0,当前灰度值]外之像素个数temp——>

拖欠区间与总像素个数的比值——>

新灰度值=原灰度值×比值——>

因新灰度值为R、G、B分量得到RGB值——>

新像素

    // 直方图均衡处理,不更改来自图像

    private BufferedImage hisEqual(BufferedImage originalImage) {

        int alph, rgb, red, green, blue, gray;

        int width = originalImage.getWidth();

        int height = originalImage.getHeight();

        double temp = 0.0;

 

        BufferedImage transimg = new BufferedImage(width, height,

                originalImage.getType());// 创建同摆放同大小的初图片

 

        for (int i = 0; i < 256; i++) {//遍历灰度直方图

            temp = 0.0;

            for (int j = 0; j <= i; j++) {//

                temp = (double) huidunum[j] + temp;

            }

            temp = (temp / (double) width) / (double) height;

            transhuidu[i] = (int) (255.0 * temp);

        }

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

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

                rgb = originalImage.getRGB(i, j);

 

                alph = rgb >> 24;

                red = (rgb & 0xff0000) >> 16;

                green = (rgb & 0xff00) >> 8;

                blue = (rgb & 0xff);

 

                gray = (int) (red * 299 + green * 587 + blue *
114) / 1000;

                gray = transhuidu[gray];// 新灰度值

                rgb = (alph << 24)|(gray << 16)|(gray
<< 8) | gray;//新RGB值

                transimg.setRGB(i, j, rgb);

            }

        }

        return transimg;

    }

 

3、private void getRecommendRange(int width, int height, int
huidunum[])

(1)    效能说明:博像素集中分布的灰度值范围

(2)       输入参数说明:老三单参数分别吗图像宽、高、各灰度值的像素个数

(3)      
输出参数说明:函数得到像素集中分别的灰度值范围,下界、上界分别存入全局变量recommendstart、recommendend

(4)    终法流程:

初始化待求区间为[0,255]——>

以i遍历huidunum[]——>

以j遍历huidunum[i,255]——>

以k遍历huidunum[i,j] 并统计是区间内像从总个数sum——>

若sum不少于总像素个数的85%还距离[i,j]长度小于上次拿走的区间长度,则获[i,j]。如此循环直到结束。

 

    // 获得源图像中占大多数底连续灰度值区间 [recommendstart,recommendend]

    private void getRecommendRange(int width, int
height, int huidunum[]) {

        double sum = 0.0;

        recommendstart = 0;

        recommendend = 255;

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

            for (int j = i; j < 256; j++) {

                sum = 0.0;

                for (int k = i; k <= j; k++) {

                    sum = sum + (double) huidunum[k];

                }

                if (sum > percentage * width * height) {

                    if (j – i < recommendend
recommendstart) {

                        recommendstart = i;

                        recommendend = j;

                    }

                }

            }

        }

}

 

 

4、**private int getNewGrayValue(int f, int a, int b, int c, int d)**

(1)    功用说明:是函数实现灰度值转换

(2)   
输入参数说明:f为原本灰度值,[b,c]为原图像灰度值集中限制,[c,d]也而关伸到的界定,由用户输入

(3)    出口参数说明:函数得到更换后的初灰度值

(4)    算是法流程:斯部分即使是
二(二)2的编程实现,比较简单不再赘述

* *

    private int getNewGrayValue(int f, int a, int b,
int c, int d) {

        int newGrayValue = f;

        if (f < a) {

            newGrayValue = (int) ((double) c * (double) f /
(double) a);

        } else if (f > b) {

            newGrayValue = (int) ((double) (f – b) *
(double) (255 – d)

                    / (double) (255 – b) + d);

        } else {

            newGrayValue = (int) ((double) (f – a) *
(double) (d – c)

                    / (double) (b – a) + c);

        }

        return newGrayValue;

}

* *

5、     private BufferedImage Linearstretch(BufferedImage
originalImage, int newgraystart, int newgrayend)

(1)    功用说明:根据用户输入的灰度值范围[newgraystart,
newgrayend]开展分段线性拉伸

(2)    输入参数说明originalImage为原本图像,[newgraystart,
newgrayend]也用户输入的灰度值范围

(3)   
输出参数说明函数执行成功后收获原图像经分段线性拉伸后底图像

(4)   算法流程

施行getRecommendRange函数获得本图像计组像素集中分布之灰度值范围——>

遍历原图像的像素——>

得到该像素的rgb值——>

赢得rgb值的分量r、g、b——>

获取灰度值gray——>

推行getNewGrayValue函数获得对应之初灰度值——>

因为gray为老三个轻重获得新rgb值——>

获新像素

 

private BufferedImage Linearstretch(BufferedImage originalImage,

            int newgraystart, int newgrayend) {

        int newhuidunum[] = new int[256];

 

        int alph, rgb, red, green, blue, gray;

        int width = originalImage.getWidth();

        int height = originalImage.getHeight();

 

        BufferedImage transimg = new BufferedImage(width, height,

                originalImage.getType());

 

        // 获得灰度大部分聚齐之范围 [recommendstart, recommendend]

        getRecommendRange(width, height, huidunum);

 

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

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

                rgb = originalImage.getRGB(i, j);

 

                alph = rgb >> 24;

                red = (rgb & 0xff0000) >> 16;

                green = (rgb & 0xff00) >> 8;

                blue = (rgb & 0xff);

 

                gray = (int) (red * 299 + green * 587 + blue *
114) / 1000;

 

                // 根据拉伸变更换得新的灰度值

                gray = getNewGrayValue(gray, recommendstart,
recommendend,

                        newgraystart, newgrayend);

                rgb = (alph << 24) | (gray << 16) | (gray
<< 8) | gray;

                transimg.setRGB(i, j, rgb);

                newhuidunum[gray]++;

            }

        }

        return transimg;

}

四、 实验

(一)灰度直方图均衡

  1. 1.      试与结果

766游戏网官网 1
 

766游戏网官网 2

 

  1. 2.      结果分析

图像经过直方图均衡处理后,图像的对比度会增长,特别是对背景或前景还太亮或太暗的图像非常实惠。

均衡化后底每灰度级更加平衡,对于灰度范围稍,直方图布最不咸匀的图像,可人为的妥的扩张灰度范围,均衡化后能获得比较好之层次感,使图像信息易得重复鲜明。

(二)分段线性拉伸

(1)      
试与结果

766游戏网官网 3

 766游戏网官网 4

766游戏网官网 5

766游戏网官网 6

 

 

(2)       结果分析

自上述实验及其结果比可看,线性变换可以将原先图像相对比集中之灰度级拉伸到到指定的灰度级范围,当灰度级范围比较原范围没有时,图像将变暗,反的则变亮。

五、 结论

直方图均衡和线性拉伸是本着数字图像进行处理的法子被的星星点点种,是点运算。

直方图均衡处理得要所有灰度级出现的相对概率一样,经过直方图均衡处理后,图像的对比度会增进,会又起层次感,特别是对此背景或前景还太亮或太暗的图像非常管用。

线性拉伸得拿原先图像集中之灰度值区间拉伸到指定的距离上,这样可突出感兴趣之靶子要灰度区间,相对抑制不感兴趣的灰度区间。

参考文献

[1] 冈萨雷斯. 数字图像处理[M]. 北京:电子工业出版社, 2011.

 

发表评论

电子邮件地址不会被公开。 必填项已用*标注