#include<stdlib.h>
#include <ctype.h>
#include <malloc.h>
#include"Similarity.h"
#include"huiduxst.h"
#define WIDTHBYTES(i) ((i+31)/32*4)
int main()
{
BITMAPFILEHEADER bf; //BMP文件头结构体
BITMAPINFOHEADER bi; //BMP信息头结构体
FILE* fp; //指向文件的指针
DWORD LineByte,ImgSize;
DWORD NumColors;
unsigned char * * Imgdata;
unsigned char * * Smlryimadata;
int i,j;
unsigned char pix[3];
fp=fopen("景甜.bmp","rb");
if(fp == NULL){
printf("Open file error!");
exit(0);
}
//读取信息头、文件头
fread(&bf,sizeof(BITMAPFILEHEADER),1,fp); //把指针fp所指向的文件的头信息写入bf(地址)
fread(&bi,sizeof(BITMAPINFOHEADER),1,fp);
LineByte=(DWORD)WIDTHBYTES(bi.biWidth*bi.biBitCount); //计算位图的实际宽度并确保它为32的倍数
ImgSize=(DWORD)LineByte*bi.biHeight;
if (bi.biClrUsed != 0 )
NumColors=(DWORD)bi.biClrUsed;
else
switch (bi.biBitCount)
{
case 1:NumColors=2;break;
case 4:NumColors=16;break;
case 8:NumColors=256;break;
case 24:NumColors=0;break;
}
//分配调色板内存
Imgdata=new unsigned char*[bi.biHeight]; //声明一个指针数组
for ( i=(bi.biHeight)-1;i>=0;i--)
Imgdata[i]=new unsigned char[bi.biWidth*3]; //每个数组元素也是一个指针数组
for ( i=(bi.biHeight)-1;i>=0;i--)
for(j=0;j<bi.biWidth*3;j++)
fread(&Imgdata[i][j],1,1,fp);//每次只读取一个1字节,存入数组
//-------------------------Skin color similarity image----------------------//
Smlryimadata =new unsigned char*[bi.biHeight];
for ( i=(bi.biHeight)-1;i>=0;i--)
Smlryimadata[i]=new unsigned char[bi.biWidth];
for (i = (bi.biHeight) - 1;i >=0;i--)
for(j=0;j<bi.biWidth;j++){
pix[0]=Imgdata[i][3*j+0];
pix[1]=Imgdata[i][3*j+1];
pix[2]=Imgdata[i][3*j+2];
Smlryimadata[i][j] = (unsigned char)Similarity(pix);
//调试的时候 观察;
}
//Smlryimadata[i][j]的值
FILE *fp1;
fp1=fopen("Smlryimadata.txt","wb");
//与接下来写入Smlryimadata.txt后
for(i=0;i<bi.biHeight;i++)
for(j=0;j<bi.biWidth;j++)
//打开后发现与原先观察的结果不同;
{
//fwrite(&Smlryimadata[i][j],1,1,fp1);
//不知道为什么用fwrite(&Smlryimadata[i]
fprintf(fp1,"%d\n",Smlryimadata[i][j]);
//[j],1,1,fp1);写入后打开是乱码?
}
//fwrite(&Smlryimadata[0][0],1,1,fp1);
//fprintf(fp1,"%d\n",Smlryimadata[0][1]);
fclose(fp1);
huiduxst(Smlryimadata,bi.biWidth,bi.biHeight);
free(Smlryimadata);
free(Imgdata);
fclose(fp);
return 0;
}
//这个函数是要将数据写入到8位的bmp文件中去,可是写入后的文件后打开总是空。而且格式和属性都与文件头信息头设定的
// 不同!
#include"huiduxst.h"
typedef unsigned long DWORD;
//typedef int BOOL;
typedef unsigned char BYTE;
typedef unsigned short WORD;
typedef long LONG;
#define BI_RGB 0L
void huiduxst(unsigned char **Imgdata, long biWidth,long biHeight){
FILE * fp;
BITMAPFILEHEADER targetfileheader;
BITMAPINFOHEADER targetinfoheader;
memset(&targetfileheader,0,sizeof(BITMAPFILEHEADER));
memset(&targetinfoheader,0,sizeof(BITMAPINFOHEADER));
//构造灰度图的文件头
targetfileheader.bfOffBits=(DWORD)sizeof(BITMAPFILEHEADER)+(DWORD)sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*256;
targetfileheader.bfSize=biWidth*biHeight+sizeof(RGBQUAD)*256 +sizeof(BITMAPFILEHEADER)+sizeof(BITMAPINFOHEADER);
targetfileheader.bfReserved1=0;
targetfileheader.bfReserved2=0;
targetfileheader.bfType=0x4d42;
//构造灰度图的信息头
targetinfoheader.biBitCount=8;
targetinfoheader.biSize=sizeof(BITMAPINFOHEADER);
targetinfoheader.biHeight=biHeight;
targetinfoheader.biWidth=biWidth;
targetinfoheader.biPlanes=1;
targetinfoheader.biCompression=BI_RGB;
targetinfoheader.biSizeImage=0;
targetinfoheader.biXPelsPerMeter=0;
targetinfoheader.biYPelsPerMeter=0;
targetinfoheader.biClrImportant=0;
targetinfoheader.biClrUsed=0;
//构造灰度图的调色版
RGBQUAD rgbquad[256];
int i,j;
FILE *fp1=fopen("灰度.txt","wb");
fwrite(*Imgdata,1,biWidth*biHeight,fp1);
fclose(fp1);
for(i=0;i<256;i++)
{
rgbquad[i].rgbBlue=i;
rgbquad[i].rgbGreen=i;
rgbquad[i].rgbRed=i;
rgbquad[i].rgbReserved=0;
}
//fclose(fopen("灰度图.bmp","w"));
fp=fopen("灰度图.bmp","wb");
fwrite(rgbquad,sizeof(RGBQUAD),256,fp);
fwrite(&targetfileheader,sizeof(BITMAPFILEHEADER),1,fp);
fwrite(&targetinfoheader,sizeof(BITMAPINFOHEADER),1,fp);
fwrite(rgbquad,sizeof(RGBQUAD),256,fp);
for (i=targetinfoheader.biHeight-1;i>=0;i--)
for (j=0 ;j<targetinfoheader.biWidth;j++) {
// Imgdata[i][j] = 255 - Imgdata[i][j];
fwrite(&Imgdata[i][j],1,1,fp);
fclose(fp);
}
}
#include"Similarity.h"
double Similarity(unsigned char p[3])
{
double simirity=0;
double c[3][3]={{0.0009,0.0022,0.0011},{0.0022,0.8209,0.4004},{0.0011,0.4004,0.2117}};
double x[3]={23.6982,121.0278,141.3382};
double xx[3];
int i,j;
for(i=0;i<=2;i++)
{
xx[i]=p[i]-x[i];
}
double xc[3]={0,0,0};
for (i=0;i<=2;i++)
{
for(j=0;j<=2;j++)
{
xc[i]+=xx[j]*c[j][i];
}
}
for(i=0;i<=2;i++)
{
simirity+=xc[i]*p[i];
}
return (255*exp(-0.5*simirity));
}
huiduxst.h:
#ifndef STDIOH
#define STDIOH
#include <stdio.h>
#endif
#include <string.h>
#include <windows.h>
void huiduxst(unsigned char **p, long ,long );
Similarity.h:
#include <math.h>
double Similarity(unsigned char p[3]);
大家好:这是我做人脸识别到时候在提取灰度相似图用到的程序。请大家帮帮忙!问题我在程序终有注释。谢谢!