📄 process.cpp
字号:
#include "stdafx.h"
#ifndef _INC_PROCESSC
#define _INC_PROCESSC
extern RGBQUAD D_pal[256];
void WINAPI histog(BYTE **list,long *pg,int x, int y, int Dx, int Dy)
{ // 统计直方图
int i,j;
for (i=0;i<256;i++) pg[i]=0;
for(i=y;i<y+Dy;i++)
for (j=x;j<x+Dx;j++)
pg[list[i][j]]++;
}
void WINAPI GT(BYTE **list,int Dx,int Dy,int* T_gray)
{ // 实现灰度变换
int i,j;
for (i=0;i<Dy;i++) {
for (j=0;j<Dx;j++) {
list[i][j]=T_gray[list[i][j]];
}
}
}
void WINAPI GT_Equal(long* pg,int* T_gray) // 直方图均衡化
{
long tt[256],sum;
int i;
sum=0;
for (i=0;i<256;i++) {
sum+=pg[i];
tt[i]=sum;
}
for (i=0;i<256;i++) {
T_gray[i]=(int) (255*tt[i]/sum);
}
}
void WINAPI Border_Equal(long* pg,int* T_gray) // 边缘图像直方图均衡化
{
long tt[256],sum;
int i,k,m,max,no;
pg[0]=pg[255]=0;
HistogSmooth(pg,10);
no=1;
max=pg[1];
for (i=2;i<255;i++) {
if (pg[i]>max) {
max=pg[i];
no=i;
}
}
no+=2;
k=pg[no]/120+1;
for (i=0;i<256;i++) pg[i]/=k;
if (no<128) {
for (k=no+1;k<250;k++)
if (pg[k-1]-pg[k]>=pg[k]-pg[k+3]) break;
m=k;
sum=0;
for (i=m;i<256;i++) {
sum+=pg[i];
tt[i]=sum;
}
for (i=0;i<m;i++) T_gray[i]=i;
for (i=m;i<256;i++) {
T_gray[i]=(int) (m+(255-m)*tt[i]/sum);
}
}
else
{
for (k=no-1;k>5;k--)
if (pg[k+1]-pg[k]>=pg[k]-pg[k-3]) break;
m=k;
sum=0;
for (i=0;i<m;i++) {
sum+=pg[i];
tt[i]=sum;
}
for (i=m;i<256;i++) T_gray[i]=i;
for (i=0;i<m;i++) {
T_gray[i]=(int) (m*tt[i]/sum);
}
}
}
void WINAPI GT_histo_eq(long *pg,long *Hista,int* T_gray) // 直方图规定化
{
int i,j,k;
long la,lb,sum,suma;
double hist[256],hista[256];
sum=suma=0;
for (i=0;i<256;i++) {
sum +=pg[i];
suma+=Hista[i];
}
la=lb=0;
for (i=0;i<256;i++) {
la+=pg[i];
hist[i] =(double) la/sum;
lb+=Hista[i];
hista[i]=(double) lb/suma;
}
for (i=0,k=0;i<256;i++) {
for (j=255;j>k;j--) {
if (hista[j]<=hist[i]) break;
}
T_gray[i]=k=j;
}
}
void WINAPI GT_linear(int* T_gray) // 分段线性化
{
int i;
for (i=0;i<64;i++)
T_gray[i]=i/2;
for (i=64;i<192;i++)
T_gray[i]=32+3*(i-64)/2;
for (i=192;i<256;i++)
T_gray[i]=128+i/2;
}
void WINAPI GT_square(int* T_gray) // 平方变换
{
int i;
for (i=0;i<256;i++)
T_gray[i]=(long) i*i /255;
}
void WINAPI GT_sqrt(int* T_gray) // 平方根变换
{
int i;
for (i=0;i<256;i++)
T_gray[i]=(int) (sqrt((double) i/255)*255);
}
void WINAPI GT_log(int* T_gray) // 对数变换
{
int i;
for (i=0;i<256;i++)
T_gray[i]=(int) ((log((double) (i+1))/log(256.0))*255);
}
void WINAPI GT_exp(int* T_gray) // 指数变换
{
int i;
for (i=0;i<256;i++)
T_gray[i]=(int)exp(log(256.0)*i/255)-1;
}
void WINAPI GT_nega(int* T_gray) // 反相变换
{
int i;
for (i=0;i<256;i++)
T_gray[i]=255-i;
}
void WINAPI DensitySegment(RGBQUAD *pal) // 伪彩色变换
{
int i;
for (i=1;i<255;i++) {
pal[i].rgbBlue =D_pal[32+i/4*9/8].rgbBlue;
pal[i].rgbGreen=D_pal[32+i/4*9/8].rgbGreen;
pal[i].rgbRed =D_pal[32+i/4*9/8].rgbRed;
}
pal[0].rgbBlue=pal[0].rgbGreen=pal[0].rgbRed=0;
pal[255].rgbBlue=pal[255].rgbGreen=pal[255].rgbRed=255;
}
void WINAPI PsendoColor(RGBQUAD *pal) // 伪彩色变换
{
int i,j;
for (i=0,j=0;i<64;i++,j+=4) {
pal[i].rgbRed=0; pal[i].rgbGreen=j;
pal[i].rgbBlue=255;
}
for (i=64,j=0;i<128;i++,j+=4) {
pal[i].rgbRed=0; pal[i].rgbGreen=255;
pal[i].rgbBlue=255-j;
}
for (i=128,j=0;i<192;i++,j+=4) {
pal[i].rgbRed=j; pal[i].rgbGreen=255;
pal[i].rgbBlue=0;
}
for (i=192,j=0;i<256;i++,j+=4) {
pal[i].rgbRed=255; pal[i].rgbGreen=255-j;
pal[i].rgbBlue=0;
}
}
//---------------------------------------------------------------------------
int Mask[3][3],Mask5[5][5],Scale,Offset; // 卷积模板和衰减因子
int Tkirsch[72]={
5,5,5,-3,0,-3,-3,-3,-3,
5,5,-3,5,0,-3,-3,-3,-3,
5,-3,-3,5,0,-3,5,-3,-3,
-3,-3,-3,5,0,-3,5,5,-3,
-3,-3,-3,-3,0,-3,5,5,5,
-3,-3,-3,-3,0,5,-3,5,5,
-3,-3,5,-3,0,5,-3,-3,5,
-3,5,5,-3,0,5,-3,-3,-3 };
// Robinson 算子
int Trobinson[72]={
1,2,1,0,0,0,-1,-2,-1,
2,1,0,1,0,-1,0,-1,-2,
1,0,-1,2,0,-2,1,0,-1,
0,-1,-2,1,0,-1,2,1,0,
-1,-2,-1,0,0,0,1,2,1,
-2,-1,0,-1,0,1,0,1,2,
-1,0,1,-2,0,2,-1,0,1,
0,1,2,-1,0,1,-2,-1,0 };
// Prewitt 算子
int Tprewitt[72]={
1,1,1,1,-2,1,-1,-1,-1,
1,1,1,1,-2,-1,1,-1,-1,
1,1,-1,1,-2,-1,1,1,-1,
1,-1,-1,1,-2,-1,1,1,1,
-1,-1,-1,1,-2,1,1,1,1,
-1,-1,1,-1,-2,1,1,1,1,
-1,1,1,-1,-2,1,-1,1,1,
1,1,1,-1,-2,1,-1,-1,1 };
int TLineDetect[36]={
-1,2,-1,-2,4,-2,-1,2,-1,
-1,-2,-1,2,4,2,-1,-2,-1,
-2,-1,2,-1,4,-1,2,-1,-2,
2,-1,-2,-1,4,-1,-2,-1,2 };
void Sobel0(BYTE **list0,BYTE **list1,int Dx,int Dy,char ch)
{
int i,j,A,B,C;
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
A = abs((list1[i-1][j+1]+2*list1[i][j+1]+list1[i+1][j+1])-
(list1[i-1][j-1]+2*list1[i][j-1]+list1[i+1][j-1]));
B = abs((list1[i+1][j-1]+2*list1[i+1][j]+list1[i+1][j+1])-
(list1[i-1][j-1]+2*list1[i-1][j]+list1[i-1][j+1]));
switch(ch) {
case 'M' :
C = (int) sqrt((double)(A*A+B*B));
// if (A>B) C = A;
// else C = B;
break;
case 'H' :
C = A;
break;
case 'V' :
C = B;
break;
default :
break;
}
C /= Scale;
if (C>255) C=255;
list0[i][j] = C;
}
}
}
void WINAPI Sobel(BYTE **list0,BYTE **list1,int Dx,int Dy) // Sobel 算法
{
Scale=4;
Sobel0(list0,list1,Dx,Dy,'M');
}
void Gradiant0(BYTE **list0,BYTE **list1,int Dx,int Dy,char ch)
{
int i,j,A,B,C;
for (i=0;i<Dy-1;i++) {
for (j=0;j<Dx-1;j++) {
if (ch=='R') {
A = abs(list1[i][j]-list1[i+1][j+1]);
B = abs(list1[i+1][j]-list1[i][j+1]);
C = A + B;
}
else {
A = abs(list1[i][j]-list1[i][j+1]);
B = abs(list1[i][j]-list1[i+1][j]);
switch(ch) {
case 'M' :
C = A + B;
break;
case 'H' :
C = A;
break;
case 'V' :
C = B;
break;
default :
break;
}
}
C *= Scale;
if (C>255) C=255;
list0[i][j] = C;
}
}
}
void WINAPI Gradiant(BYTE **list0,BYTE **list1,int Dx,int Dy)
{ // 梯度法
Scale=2;
Gradiant0(list0,list1,Dx,Dy,'M');
}
void WINAPI Roberts(BYTE **list0,BYTE **list1,int Dx,int Dy)
{ // roberts 梯度
Scale=2;
Gradiant0(list0,list1,Dx,Dy,'R');
}
void WINAPI Template(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
int i,j,g;
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
g = (Mask[0][0]*list1[i-1][j-1]+Mask[0][1]*list1[i-1][j]
+Mask[0][2]*list1[i-1][j+1]+Mask[1][0]*list1[i][j-1]
+Mask[1][1]*list1[i][j] +Mask[1][2]*list1[i][j+1]
+Mask[2][0]*list1[i+1][j-1]+Mask[2][1]*list1[i+1][j]
+Mask[2][2]*list1[i+1][j+1])/Scale+Offset;
if (g>0xff) g=0xff;
else if (g<0) g=0;
list0[i][j] = (BYTE) g;
}
}
}
void WINAPI Laplacian(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
Scale=1;
Offset=1;
Mask[0][0]=Mask[0][2]=Mask[2][0]=Mask[2][2]=-1;
Mask[0][1]=Mask[2][1]=Mask[1][0]=Mask[1][2]=-1;
Mask[1][1]=8;
Template(list0,list1,Dx,Dy);
Offset=0;
}
void WINAPI LapSketch(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
Scale=1;
Offset=254;
Mask[0][0]=Mask[0][2]=Mask[2][0]=Mask[2][2]=-1;
Mask[0][1]=Mask[2][1]=Mask[1][0]=Mask[1][2]=-1;
Mask[1][1]=8;
Template(list0,list1,Dx,Dy);
Offset=0;
}
void WINAPI BoundEnhance(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
Scale=4;
Mask[0][0]=Mask[0][2]=Mask[2][0]=Mask[2][2]=0;
Mask[0][1]=Mask[2][1]=Mask[1][0]=Mask[1][2]=-1;
Mask[1][1]=Scale+4;
Template(list0,list1,Dx,Dy);
}
void WINAPI RemoveLineNoise(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
Scale=3;
Mask[0][1]=Mask[1][1]=Mask[2][1]=1;
Mask[0][0]=Mask[0][2]=0;
Mask[1][0]=Mask[1][2]=0;
Mask[2][0]=Mask[2][2]=0;
Template(list0,list1,Dx,Dy);
}
void WINAPI Smooth5(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
Scale=5;
Mask[0][0]=Mask[0][2]=Mask[2][0]=Mask[2][2]=0;
Mask[0][1]=Mask[2][1]=Mask[1][0]=Mask[1][2]=1;
Mask[1][1]=1;
Template(list0,list1,Dx,Dy);
}
void WINAPI Smooth9(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
Scale=9;
Mask[0][0]=Mask[0][2]=Mask[2][0]=Mask[2][2]=1;
Mask[0][1]=Mask[2][1]=Mask[1][0]=Mask[1][2]=1;
Mask[1][1]=1;
Template(list0,list1,Dx,Dy);
}
void WINAPI RemoveWhiteDot(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
int i,j,k,m,s,t;
m=2;
for (i=0;i<Dy;i++)
memcpy(list0[i],list1[i],Dx);
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
if (list1[i][j]) {
k=0;
for (t=-1;t<2;t++) {
for (s=-1;s<2;s++) {
if (list1[i+t][j+s]) k++;
if (k>m) break;
}
if (k>m) break;
}
if (k<m+1) list0[i][j]=0;
}
}
}
}
void WINAPI RemoveBlackDot(BYTE **list0,BYTE **list1,int Dx,int Dy)
{
int i,j,k,s,t;
for (i=0;i<Dy;i++)
memcpy(list0[i],list1[i],Dx);
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
if (list1[i][j]==0) {
k=0;
for (t=-1;t<2;t++) {
for (s=-1;s<2;s++) {
if (list1[i+t][j+s]==0) k++;
if (k>3) break;
}
if (k>3) break;
}
if (k<4) list0[i][j]=255;
}
}
}
}
int MedValue(int *buf, int n, int m) // 排序取中值
{
int i,j,k,f;
for (i=1;i<n;i++) {
f=0;
for (j=n-1;j>=i;j--) {
if (buf[j]>buf[j+1]) {
k=buf[j]; buf[j]=buf[j+1];
buf[j+1]=k; f=1;
}
}
if (f==0) break;
}
return(buf[m]);
}
void Median(BYTE **list0, BYTE **list1, int Dx, int Dy, int flag)
{
int i,j,buff1[20];
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
buff1[0] = list1[i-1][j];
buff1[1] = list1[i][j];
buff1[2] = list1[i+1][j];
buff1[3] = list1[i][j-1];
buff1[4] = list1[i][j+1];
if (flag==9) {
buff1[5] = list1[i-1][j-1];
buff1[6] = list1[i-1][j+1];
buff1[7] = list1[i+1][j-1];
buff1[8] = list1[i+1][j+1];
}
list0[i][j] = (BYTE) MedValue(buff1, flag, flag/2);
}
}
}
void WINAPI Median5(BYTE **list0,BYTE **list1,int Dx,int Dy)
{ // 3x3邻域五点中值滤波
Median(list0,list1,Dx,Dy,5);
}
void WINAPI Median9(BYTE **list0,BYTE **list1,int Dx,int Dy)
{ // 3x3邻域九点中值滤波
Median(list0,list1,Dx,Dy,9);
}
int WINAPI LineWidthW(BYTE **list,int x,int y,int n)
{
int i,t;
int Mask3[9][2] ={{ 1, 0},{ 1,-1},{ 0,-1},{-1,-1},
{-1, 0},{-1, 1},{ 0, 1},{ 1, 1},{ 1, 0}};
for (i=0,t=0; i<=8; i++) {
if (list[y+Mask3[i][1]][x+Mask3[i][0]]>=n) {
t++;
if (t>1) break;
}
else t=0;
}
return(t);
}
void WINAPI OnePWidthW(BYTE **list0,BYTE **list1,int Dx,int Dy) // 边界宽度单点化
{
int i,j,n,l,k,p,t;
for(i=0;i<Dy;i++)
memset(list0[i],0,Dx);
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
if (list1[i][j]==0) continue;
n=0;
p=list1[i][j];
for (l=-1;l<2;l++) {
for (k=-1;k<2;k++)
if (list1[i+l][j+k]>=p) n++;
}
if (n>3) {
t=LineWidthW(list1,j,i,p);
if (t<2) list0[i][j]=p;
}
else if (n==3) {
if (list1[i][j-1]>p) {
if ((list1[i-1][j]>p)||(list1[i+1][j]>p)) n--;
}
else if (list1[i][j+1]>p) {
if ((list1[i-1][j]>p)||(list1[i+1][j]>p)) n--;
}
if (n==3) list0[i][j]=p;
}
else list0[i][j]=p;
}
}
for (i=1;i<Dy-1;i++) {
for (j=1;j<Dx-1;j++) {
if (list0[i][j]==0) continue;
for (l=-1,n=0;l<2;l++) {
for (k=-1;k<2;k++)
if (list0[i+l][j+k]>0) n++;
}
if (n==1) list0[i][j]=0;
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -