您的位置:首页 > 编程语言 > Java开发

图像处理之高斯模糊

2012-02-05 14:51 423 查看
高斯模糊是一种两维的卷积模糊操作,在图像完成高斯模糊相对于均值模糊来说,
计算量会增加,但是高斯模糊可以实现一些特殊效果,特别是在图像噪声(非椒盐
噪声)消去方面,更是有着非常好的效果。一维高斯公式如下:



其中x是制定[-n,n]范围的整数,sigma代表标准方差。通常取值为1.
一维高斯函数Java代码如下:
private float[] get1DKernalData(int n, float sigma) { 		float sigma22 = 2*sigma*sigma; 		float Pi2 = 2*(float)Math.PI; 		float sqrtSigmaPi2 = (float)Math.sqrt(Pi2) * sigma ; 		int size = 2*n + 1; 		int index = 0; 		float[] kernalData = new float[size]; 		for(int i=-n; i<=n; i++) { 			float distance = i*i; 			kernalData[index] = (float)Math.exp((-distance)/sigma22)/sqrtSigmaPi2; 			System.out.println("\t" + kernalData[index]); 			index++; 		} 		return kernalData; 	}
假设输入 n= 1, sigma = 1时,输出的Kernel数据为:
0.24197073, 0.3989423, 0.24197073
两维的高斯分布函数为:


对应的Java实现代码为:
public float[][] get2DKernalData(int n, float sigma) { 		int size = 2*n +1; 		float sigma22 = 2*sigma*sigma; 		float sigma22PI = (float)Math.PI * sigma22; 		float[][] kernalData = new float[size][size]; 		int row = 0; 		for(int i=-n; i<=n; i++) { 			int column = 0; 			for(int j=-n; j<=n; j++) { 				float xDistance = i*i; 				float yDistance = j*j; 				kernalData[row][column] = (float)Math.exp(-(xDistance + yDistance)/sigma22)/sigma22PI; 				column++; 			} 			row++; 		} 		 		for(int i=0; i<size; i++) { 			for(int j=0; j<size; j++) { 				System.out.print("\t" + kernalData[i][j]); 			} 			System.out.println(); 			System.out.println("\t ---------------------------"); 		} 		return kernalData; 	}
当n=1, sigma=1时对应输出的Kernel数据为: 0.058549833 0.09653235 0.058549833 0.09653235 0.15915494 0.09653235 0.058549833 0.09653235 0.058549833 一个2D高斯分布的图可以表示如下:


高斯过滤在图像处理是一种低通滤波,会除去图像的细节而保持整体不变化,在图像美化和特效 方面,高斯过滤有这很多应用。高斯模糊不同于均值模糊! 本文实现完整的高斯模糊算法包括下面几个步骤: 1. 生成高斯操作数即Kernel Data 2. 从图像中读取像素,利用第一步的操作数,完成卷积。 3. 发现图像处理前后的最大像素值peak得出rate 4. 完成归一化操作,返回处理后像素数组
关键程序解析: 利用操作数完成卷积的代码参看以前的Blog文章《图像处理之理解卷积》 完成归一化操作的算法非常简单, 主要是利用第三步计算出来的rate
// normalization         float rate = inMax/outMax;         System.out.println("Rate = " + rate);         for(int row=0; row<height; row++) {         	for(int col=0; col<width; col++) {         		index = row * width + col;         		int rgb1 = tempoutPixels[index]; 				int red = (rgb1 >> 16) & 0xff; 				int green = (rgb1 >> 8) & 0xff; 				int blue = rgb1 & 0xff; 				red = (int)(rate * red); 				green = (int)(rate * green); 				blue = (int)(rate * blue); 				outPixels[index] = (rgb1 & 0xff000000) | (red << 16) | (green << 8) | blue;         	}         }

高斯模糊效果如下:


- 左边为原图 - 右边为高斯模糊之后效果,发现皱纹和手部滑了 等等现在还不最cool的效果,高斯模糊之后如果与原图像叠加会出现一种Glow的 效果,好像灯光打在图像上一样,Glow处理之后的运行效果如下: 原图:


实现Glow Filter之后的图像:


实现Glow算法只是高斯模糊输出像素值叠加原来的像素值。
int index = 0; 		for ( int y = 0; y < height; y++ ) { 			for ( int x = 0; x < width; x++ ) { 				int rgb1 = outPixels[index]; 				int r1 = (rgb1 >> 16) & 0xff; 				int g1 = (rgb1 >> 8) & 0xff; 				int b1 = rgb1 & 0xff;  				int rgb2 = inPixels[index]; 				int r2 = (rgb2 >> 16) & 0xff; 				int g2 = (rgb2 >> 8) & 0xff; 				int b2 = rgb2 & 0xff;  				r1 = PixelUtils.clamp( (int)(r1 + a * r2) ); 				g1 = PixelUtils.clamp( (int)(g1 + a * g2) ); 				b1 = PixelUtils.clamp( (int)(b1 + a * b2) );  				inPixels[index] = (rgb1 & 0xff000000) | (r1 << 16) | (g1 << 8) | b1; 				index++; 			} 		}

转载时请注明出处!!,谢谢!
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息