⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 filters.cs

📁 数图空域滤波器 灰度图有效 C# dll装配件
💻 CS
📖 第 1 页 / 共 2 页
字号:
using System;
using System.Drawing;
using System.Drawing.Imaging;

namespace MyApp.Filters
{
	/// <summary>
	/// Summary description for Class1.
	/// </summary>
	public class filters							//滤波函数类
	{	
		private int[][] Average;					//均值矩阵					

		private int[][] Sobel1;						//Sobel算子矩阵
		private int[][] Sobel2;

		private int[][] Prewitt1;					//Prewitt算子矩阵
		private int[][] Prewitt2;

		private int[][] Kirsch1;					//Kirsch算子矩阵
		private int[][] Kirsch2;
		private int[][] Kirsch3;
		private int[][] Kirsch4;
		private int[][] Kirsch5;
		private int[][] Kirsch6;
		private int[][] Kirsch7;
		private int[][] Kirsch8;

		private int[][] Laplacian;					//laplacian算子矩阵

		private int[][] BitmapArray;				//灰度矩阵
		private int nWidth;							//图宽
		private int nHeight;						//图高

		private double sigma=0.36;					//sigma系数

		private int[][] dotlight;

		public filters()
		{
			//以下是初始化各个算子矩阵
			InitAverage();
			InitSobel();
			InitPrewitt();
			InitKirsch();
			InitLaplacian();
			InitDotLight();
		}

		public void Bitmap2Array(Bitmap b)			//位图转灰度矩阵
		{
			BitmapData bmData = b.LockBits(new Rectangle(0, 0, b.Width, b.Height), ImageLockMode.ReadWrite,b.PixelFormat);
			int stride = bmData.Stride;
			System.IntPtr Scan0 = bmData.Scan0;
			BitmapArray=new int[b.Height][];

			unsafe //以下为不受管制的c#
			{
				byte * p = (byte *)(void *)Scan0;

				int nOffset = stride - b.Width*3;
				nWidth = b.Width;
				nHeight= b.Height; 

				for(int y=0;y<nHeight;y++)
				{
					BitmapArray[y]=new int[b.Width];
					for(int x=0; x < nWidth; x++ )
					{
						BitmapArray[y][x]=p[0];
						p += 3;
					}
					p += nOffset;
				}
			}
			b.UnlockBits(bmData);
		}
		public int[][] GetBitmapArray(Bitmap b)					//同上
		{
			BitmapData bmData = b.LockBits(new Rectangle(0, 0, b.Width, b.Height), ImageLockMode.ReadWrite,b.PixelFormat);
			int stride = bmData.Stride;
			System.IntPtr Scan0 = bmData.Scan0;
			int[][] Array=new int[b.Height][];

			unsafe 
			{
				byte * p = (byte *)(void *)Scan0;

				int nOffset = stride - b.Width*3;
				nWidth = b.Width;
				nHeight= b.Height; 

				for(int y=0;y<nHeight;y++)
				{
					Array[y]=new int[b.Width];
					for(int x=0; x < nWidth; x++ )
					{
						Array[y][x]=p[0];
						p += 3;
					}
					p += nOffset;
				}
			}
			b.UnlockBits(bmData);
			return Array;
		}
		private double[][] GetArray(Bitmap myBitmap)				//同上
		{
			int height=myBitmap.Height;
			int width=myBitmap.Width;

			double[][] array=new double[height][];
			int i,j;
			for(i=0;i<=height-1;i++)
			{
				array[i]=new double[width];
				for(j=0;j<=width-1;j++)
				{
					array[i][j]=myBitmap.GetPixel(j,i).R;
				}
			}
			return array;
		}

		private void GetMatch(double[][] array1,double[][] array2)		//算出匹配矩阵
		{
			//double temp1=(double[][])array1.Clone();
			//double temp2=(double[][])array2.Clone();

		}

		public double GetError(Bitmap myBitmap1,Bitmap myBitmap2)		//算均方差
		{
			double[][] array1=GetArray(myBitmap1);
			double[][] array2=GetArray(myBitmap2);
			GetMatch(array1,array2);
			double re=0;
			for(int i=0;i<=array1.Length-1;i++)
				for(int j=0;j<=array1[0].Length-1;j++)
				{
					re+=Math.Pow((array1[i][j]-array2[i][j]),2);
				}
			re=re/(array1.Length*array1[0].Length);
			re=Math.Sqrt(re);
			return re;
		}
		private void InitDotLight()
		{
			dotlight=new int[5][];
			dotlight[0]=new int[5];
			dotlight[0][0]=0;
			dotlight[0][1]=1;
			dotlight[0][2]=2;
			dotlight[0][3]=1;
			dotlight[0][4]=0;
			dotlight[1]=new int[5];
			dotlight[1][0]=1;
			dotlight[1][1]=4;
			dotlight[1][2]=8;
			dotlight[1][3]=4;
			dotlight[1][4]=1;
			dotlight[2]=new int[5];
			dotlight[2][0]=2;
			dotlight[2][1]=8;
			dotlight[2][2]=16;
			dotlight[2][3]=8;
			dotlight[2][4]=2;
			dotlight[3]=new int[5];
			dotlight[3][0]=1;
			dotlight[3][1]=4;
			dotlight[3][2]=8;
			dotlight[3][3]=4;
			dotlight[3][4]=1;
			dotlight[4]=new int[5];
			dotlight[4][0]=0;
			dotlight[4][1]=1;
			dotlight[4][2]=2;
			dotlight[4][3]=1;
			dotlight[4][4]=0;
		}
		
		private void InitLaplacian()
		{
			Laplacian=new int[3][];
			Laplacian[0]=new int[3];
			Laplacian[0][0]=1;
			Laplacian[0][1]=1;
			Laplacian[0][2]=1;
			Laplacian[1]=new int[3];
			Laplacian[1][0]=1;
			Laplacian[1][1]=-8;
			Laplacian[1][2]=1;
			Laplacian[2]=new int[3];
			Laplacian[2][0]=1;
			Laplacian[2][1]=1;
			Laplacian[2][2]=1;
		}
		private void InitAverage()
		{
			Average=new int[3][];
			for(int i=0;i<=2;i++)
			{
				Average[i]=new int[3];
				for(int j=0;j<=2;j++)
				{
					Average[i][j]=1;
				}
			}
		}

		private void InitKirsch()
		{
			Kirsch1=new int[3][];
			Kirsch1[0]=new int[3];
			Kirsch1[0][0]=5;
			Kirsch1[0][1]=5;
			Kirsch1[0][2]=5;
			Kirsch1[1]=new int[3];
			Kirsch1[1][0]=-3;
			Kirsch1[1][1]=0;
			Kirsch1[1][2]=-3;
			Kirsch1[2]=new int[3];
			Kirsch1[2][0]=-3;
			Kirsch1[2][1]=-3;
			Kirsch1[2][2]=-3;

			Kirsch2=new int[3][];
			Kirsch2[0]=new int[3];
			Kirsch2[0][0]=-3;
			Kirsch2[0][1]=5;
			Kirsch2[0][2]=5;
			Kirsch2[1]=new int[3];
			Kirsch2[1][0]=-3;
			Kirsch2[1][1]=0;
			Kirsch2[1][2]=5;
			Kirsch2[2]=new int[3];
			Kirsch2[2][0]=-3;
			Kirsch2[2][1]=-3;
			Kirsch2[2][2]=-3;

			Kirsch3=new int[3][];
			Kirsch3[0]=new int[3];
			Kirsch3[0][0]=-3;
			Kirsch3[0][1]=-3;
			Kirsch3[0][2]=5;
			Kirsch3[1]=new int[3];
			Kirsch3[1][0]=-3;
			Kirsch3[1][1]=0;
			Kirsch3[1][2]=5;
			Kirsch3[2]=new int[3];
			Kirsch3[2][0]=-3;
			Kirsch3[2][1]=-3;
			Kirsch3[2][2]=5;

			Kirsch4=new int[3][];
			Kirsch4[0]=new int[3];
			Kirsch4[0][0]=-3;
			Kirsch4[0][1]=-3;
			Kirsch4[0][2]=-3;
			Kirsch4[1]=new int[3];
			Kirsch4[1][0]=-3;
			Kirsch4[1][1]=0;
			Kirsch4[1][2]=5;
			Kirsch4[2]=new int[3];
			Kirsch4[2][0]=-3;
			Kirsch4[2][1]=5;
			Kirsch4[2][2]=5;

			Kirsch5=new int[3][];
			Kirsch5[0]=new int[3];
			Kirsch5[0][0]=-3;
			Kirsch5[0][1]=-3;
			Kirsch5[0][2]=-3;
			Kirsch5[1]=new int[3];
			Kirsch5[1][0]=-3;
			Kirsch5[1][1]=0;
			Kirsch5[1][2]=-3;
			Kirsch5[2]=new int[3];
			Kirsch5[2][0]=5;
			Kirsch5[2][1]=5;
			Kirsch5[2][2]=5;

			Kirsch6=new int[3][];
			Kirsch6[0]=new int[3];
			Kirsch6[0][0]=-3;
			Kirsch6[0][1]=-3;
			Kirsch6[0][2]=-3;
			Kirsch6[1]=new int[3];
			Kirsch6[1][0]=5;
			Kirsch6[1][1]=0;
			Kirsch6[1][2]=-3;
			Kirsch6[2]=new int[3];
			Kirsch6[2][0]=5;
			Kirsch6[2][1]=5;
			Kirsch6[2][2]=-3;

			Kirsch7=new int[3][];
			Kirsch7[0]=new int[3];
			Kirsch7[0][0]=5;
			Kirsch7[0][1]=-3;
			Kirsch7[0][2]=-3;
			Kirsch7[1]=new int[3];
			Kirsch7[1][0]=5;
			Kirsch7[1][1]=0;
			Kirsch7[1][2]=-3;
			Kirsch7[2]=new int[3];
			Kirsch7[2][0]=5;
			Kirsch7[2][1]=-3;
			Kirsch7[2][2]=-3;

			Kirsch8=new int[3][];
			Kirsch8[0]=new int[3];
			Kirsch8[0][0]=5;
			Kirsch8[0][1]=5;
			Kirsch8[0][2]=-3;
			Kirsch8[1]=new int[3];
			Kirsch8[1][0]=5;
			Kirsch8[1][1]=0;
			Kirsch8[1][2]=-3;
			Kirsch8[2]=new int[3];
			Kirsch8[2][0]=-3;
			Kirsch8[2][1]=-3;
			Kirsch8[2][2]=-3;
		}

		private void InitSobel()
		{
			Sobel1=new int[3][];
			Sobel1[0]=new int[3];
			Sobel1[0][0]=-1;
			Sobel1[0][1]=0;
			Sobel1[0][2]=1;
			Sobel1[1]=new int[3];
			Sobel1[1][0]=-2;
			Sobel1[1][1]=0;
			Sobel1[1][2]=2;
			Sobel1[2]=new int[3];
			Sobel1[2][0]=-1;
			Sobel1[2][1]=0;
			Sobel1[2][2]=1;

			Sobel2=new int[3][];
			Sobel2[0]=new int[3];
			Sobel2[0][0]=-1;
			Sobel2[0][1]=-2;
			Sobel2[0][2]=-1;
			Sobel2[1]=new int[3];
			Sobel2[1][0]=0;
			Sobel2[1][1]=0;
			Sobel2[1][2]=0;
			Sobel2[2]=new int[3];
			Sobel2[2][0]=1;
			Sobel2[2][1]=2;
			Sobel2[2][2]=1;
		}

		private void InitPrewitt()
		{
			Prewitt1=new int[3][];
			Prewitt1[0]=new int[3];
			Prewitt1[0][0]=-1;
			Prewitt1[0][1]=-1;
			Prewitt1[0][2]=-1;
			Prewitt1[1]=new int[3];
			Prewitt1[1][0]=0;
			Prewitt1[1][1]=0;
			Prewitt1[1][2]=0;
			Prewitt1[2]=new int[3];
			Prewitt1[2][0]=1;
			Prewitt1[2][1]=1;
			Prewitt1[2][2]=1;

			Prewitt2=new int[3][];
			Prewitt2[0]=new int[3];
			Prewitt2[0][0]=-1;
			Prewitt2[0][1]=0;
			Prewitt2[0][2]=1;
			Prewitt2[1]=new int[3];
			Prewitt2[1][0]=-1;
			Prewitt2[1][1]=0;
			Prewitt2[1][2]=1;
			Prewitt2[2]=new int[3];
			Prewitt2[2][0]=-1;
			Prewitt2[2][1]=0;
			Prewitt2[2][2]=1;
		}
	
		private void MySetPixel(int x,int y,Bitmap b,byte color)			//写像素
		{
			BitmapData bmData = b.LockBits(new Rectangle(0, 0, b.Width, b.Height), ImageLockMode.ReadWrite,b.PixelFormat);
			int stride = bmData.Stride;
			System.IntPtr Scan0 = bmData.Scan0;

			unsafe 
			{
				byte * p = (byte *)(void *)Scan0;

				int nOffset = stride - b.Width*3;
				nWidth = b.Width;
				nHeight= b.Height; 
 
				p+=(nOffset+nWidth*3)*(y-1)+(x-1)*3;
				p[0]=color;
				p[1]=color;
				p[2]=color;
			}
			b.UnlockBits(bmData);
		}
		private byte MyGetPixel(int x,int y,Bitmap b)						//取像素
		{
			BitmapData bmData = b.LockBits(new Rectangle(0, 0, b.Width, b.Height), ImageLockMode.ReadWrite,b.PixelFormat);
			int stride = bmData.Stride;
			System.IntPtr Scan0 = bmData.Scan0;
			byte re;

			unsafe 
			{
				byte * p = (byte *)(void *)Scan0;

				int nOffset = stride - b.Width*3;
				nWidth = b.Width;
				nHeight= b.Height; 
 
				p+=(nOffset+nWidth*3)*(y-1)+(x-1)*3;
				re=p[0];
				
			}
			b.UnlockBits(bmData);
			return re;
		}

		private int[][] BlearArray(Bitmap myBitmap,int width,int height)
		{
			int[][] array=new int[5][];

			for(int i=0;i<=4;i++)
			{
				array[i]=new int[5];
				for(int j=0;j<=4;j++)
				{
					if(width-2+i>=0&&width-2+i<=myBitmap.Width-1&&height-2+j>=0&&height-2+j<=myBitmap.Height-1)
						array[i][j]=myBitmap.GetPixel(width-2+i,height-2+j).R;
					else array[i][j]=999;
				}
			}
			return array;
		}
		
		private void DotLightPixel(Bitmap myBitmap,int width,int height,int[][] array)		//均值窗
		{
			int sum=0;
			int flag=0;
			for(int i=0;i<=4;i++)
				for(int j=0;j<=4;j++)
				{
					if(array[i][j]!=999)
					{
						sum+=dotlight[i][j]*array[i][j];
					}
					else 
					{
						flag=1;
					}
				}
			sum=sum/80;
			if(flag==1) sum=array[2][2];
			else if(sum>255) sum=255;
			else if(sum<0) sum=0;			
			myBitmap.SetPixel(width,height,Color.FromArgb(sum,sum,sum));
		}
		
		public Bitmap Filter_Blear(Bitmap myBitmap)	//alpha修饰滤波
		{
			int width=myBitmap.Width;
			int height=myBitmap.Height;
			Bitmap clone=new Bitmap(width,height);

			for(int i=0;i<=height-1;i++)
				for(int j=0;j<=width-1;j++)
					DotLightPixel(clone,j,i,BlearArray(myBitmap,j,i));
			return clone;
		}


		private double[][] BlearArray(double[][] array1,int width,int height)
		{
			double[][] array=new double[5][];

			for(int i=0;i<=4;i++)
			{
				array[i]=new double[5];
				for(int j=0;j<=4;j++)
				{
					if(width-2+i>=0&&width-2+i<=array1[0].Length-1&&height-2+j>=0&&height-2+j<=array1.Length-1)
						array[i][j]=array1[height-2+j][width-2+i];
					else array[i][j]=999;
				}
			}
			return array;
		}

		public Bitmap Iterate(Bitmap myBitmap,double lamda,int c)
		{
			double[][] array_g=GetArray(myBitmap);
			int flag=0;
			double[][] array_f=NumMulArray(array_g,lamda);
			int cc=0;

			double tempError=0;
			while(flag==0)
			{
				double[][] temp_f=GetClone(array_f);
				for(int i=0;i<temp_f.Length;i++)
					for(int j=0;j<temp_f[0].Length;j++)
					{
						array_f[i][j]=temp_f[i][j]+lamda*(array_g[i][j]-conv(BlearArray(temp_f,j,i)));
					}
				//flag=Condition(epthilon,array_g,array_f,lamda);
				double error=Condition(array_f,temp_f);
				//if(Math.Abs(tempError-error)/tempError<0.5&&lamda>0.1) lamda=lamda/2;				
				if(Math.Abs(tempError-error)/tempError<0.5) lamda=lamda/2;
				tempError=error;
				cc++;
				if(cc==c) break;
			}
			Bitmap b=Array2Bitmap(array_f);
			return b;
		}
		private double[][] GetClone(double[][] array)
		{
			double[][] re=new double[array.Length][];
			for(int i=0;i<=re.Length-1;i++)
			{
				re[i]=new double[array[i].Length];
				for(int j=0;j<re[i].Length;j++)
					re[i][j]=array[i][j];
			}
			return re;
		}
		private Bitmap Array2Bitmap(double[][] array)
		{
			Bitmap b=new Bitmap(array[0].Length,array.Length);
			for(int i=0;i<array.Length;i++)
				for(int j=0;j<array[0].Length;j++)
				{
					int cl=(int)array[i][j];
					if(cl>255) cl=255;
					if(cl<0) cl=0;
					b.SetPixel(j,i,Color.FromArgb(cl,cl,cl));
				}
			return b;
		}
		private double Condition(double[][] temp_f,double[][] array_f)
		{
			int flag=0;
			double sum=0;
			for(int i=0;i<array_f.Length;i++)
				for(int j=0;j<array_f[0].Length;j++)
				{
					sum+=Math.Pow(array_f[i][j]-temp_f[i][j],2);
				}
			return sum;
		}
		private double conv(double[][] array)
		{
			double sum=0;
			int flag=0;
			for(int i=0;i<=4;i++)
				for(int j=0;j<=4;j++)
				{
					if(array[i][j]!=999)
					{
						sum+=(double)dotlight[i][j]*array[i][j];
					}
					else 
					{
						flag=1;
					}
				}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -