c语言实现BMP图像转换为灰度图
当初是自己要装X,非要用c来写信息隐藏作业,装了X,就得付出实践。查了好久资料,到期末才把作业交了,这里总结一下。
这道题是将真彩图转换为灰度图。
- 关于BMP文件结构,这是困扰了我好久的问题,上网查了很久图片的知识才弄明白
- BMP文件包括以下几部分(具体结构在程序中说明):
- 位图文件头
- 位图信息头
- 调色板
- 位图数据
- 结构体内存对齐原则对于pragma pack(n)
- 当成员大小小于n时,每个成员存储的起始位置要从该成员大小的整数倍开始,否则从n的整数倍开始
- 成员是结构体时相对于起始偏移是以其内部最大成员为准
- 当n大于内部最大成员时,结构体的总大小是其内部最大成员的整数倍反之为n的整数倍
- 32位默认n为4,64位默认为8
- 因此在定义头结构的时候要加上#pragma pack(1),设置以1字节为对齐方式,不然后面数据会错位
/*
真彩图转换成灰度图的改进版
(不把真彩图的每个像素点放入二维矩阵,而是读一行写一行)
blog:http://www.cnblogs.com/wd1001/
2015年6月2日19:04:09
*/
#include<stdio.h>
#include<malloc.h>
#include<stdlib.h>
/*
位图头结构
*/
#pragma pack(1)
typedef struct tagBITMAPFILEHEADER
{
unsigned char bfType[];//文件格式
unsigned long bfSize;//文件大小
unsigned short bfReserved1;//保留
unsigned short bfReserved2;
unsigned long bfOffBits; //DIB数据在文件中的偏移量
}fileHeader;
#pragma pack()
/*
位图数据信息结构
*/
#pragma pack(1)
typedef struct tagBITMAPINFOHEADER
{
unsigned long biSize;//该结构的大小
long biWidth;//文件宽度
long biHeight;//文件高度
unsigned short biPlanes;//平面数
unsigned short biBitCount;//颜色位数
unsigned long biCompression;//压缩类型
unsigned long biSizeImage;//DIB数据区大小
long biXPixPerMeter;
long biYPixPerMeter;
unsigned long biClrUsed;//多少颜色索引表
unsigned long biClrImporant;//多少重要颜色
}fileInfo;
#pragma pack()
/*
调色板结构
*/
#pragma pack(1)
typedef struct tagRGBQUAD
{
unsigned char rgbBlue; //蓝色分量亮度
unsigned char rgbGreen;//绿色分量亮度
unsigned char rgbRed;//红色分量亮度
unsigned char rgbReserved;
}rgbq;
#pragma pack() int main()
{
/*存储RGB图像的一行像素点*/
unsigned char ImgData[][];
/*将灰度图的像素存到一个一维数组中*/
unsigned char ImgData2[];
int i,j,k;
FILE * fpBMP,* fpGray;
fileHeader * fh;
fileInfo * fi;
rgbq * fq; if((fpBMP=fopen("G:/vc6.0/work/21.bmp","rb"))==NULL)
{
printf("打开文件失败");
exit();
} if((fpGray=fopen("G:/vc6.0/work/22.bmp","wb"))==NULL)
{
printf("创建文件失败");
exit();
} fh=(fileHeader *)malloc(sizeof(fileHeader));
fi=(fileInfo *)malloc(sizeof(fileInfo));
//读取位图头结构和信息头
fread(fh,sizeof(fileHeader),,fpBMP);
fread(fi,sizeof(fileInfo),,fpBMP);
//修改头信息
fi->biBitCount=;
fi->biSizeImage=( (fi->biWidth*+)/ ) * *fi->biHeight;
//fi->biClrUsed=256; fh->bfOffBits = sizeof(fileHeader)+sizeof(fileInfo)+*sizeof(rgbq);
fh->bfSize = fh->bfOffBits + fi->biSizeImage; //创建调色版
fq=(rgbq *)malloc(*sizeof(rgbq));
for(i=;i<;i++)
{
fq[i].rgbBlue=fq[i].rgbGreen=fq[i].rgbRed=i;
//fq[i].rgbReserved=0;
}
//将头信息写入
fwrite(fh,sizeof(fileHeader),,fpGray);
fwrite(fi,sizeof(fileInfo),,fpGray);
fwrite(fq,sizeof(rgbq),,fpGray);
//读取RGB图像素并转换为灰度值
for ( i=;i<fi->biHeight;i++ )
{
for(j=;j<(fi->biWidth+)/*;j++)
{
for(k=;k<;k++)
fread(&ImgData[j][k],,,fpBMP);
}
for(j=;j<(fi->biWidth+)/*;j++)
{
ImgData2[j]=int( (float)ImgData[j][] * 0.114 +
(float)ImgData[j][] * 0.587 +
(float)ImgData[j][] * 0.299 );
}
//将灰度图信息写入
fwrite(ImgData2,j,,fpGray);
} free(fh);
free(fi);
free(fq);
fclose(fpBMP);
fclose(fpGray);
printf("success\n");
return ;
}
结果:
c语言实现BMP图像转换为灰度图的更多相关文章
- 【Python开发】python PIL读取图像转换为灰度图及另存为其它格式(也可批量改格式)
例如有一幅图,文件名为"a.jpg'. 读取: from PIL import Image #或直接import Image im = Image.open('a.jpg') 将图片转换成 ...
- 从视频文件中读入数据-->将数据转换为灰度图-->对图像做canny边缘检测-->将这三个结构显示在一个图像中
//从视频文件中读入数据-->将数据转换为灰度图-->对图像做canny边缘检测-->将这三个结构显示在一个图像中 //作者:sandy //时间:2015-10-10 #inclu ...
- 机器学习进阶-图像基本处理-视频的读取与处理 1.cv2.VideoCapture(视频的载入) 2.vc.isOpened(载入的视频是否可以打开) 3.vc.read(视频中一张图片的读取) 4.cv2.cvtColor(将图片转换为灰度图)
1.vc = cv2.VideoCapture('test.mp4') #进行视频的载入 2.vc.isOpened() # 判断载入的视频是否可以打开 3.ret, frame = vc.read( ...
- Android-将RGB彩色图转换为灰度图
package com.example.yanlei.wifi; import android.graphics.Bitmap; import android.graphics.BitmapFacto ...
- Qt 中彩色图像转换为灰度图
近期在做几个图像处理相关的项目.里面有一个操作就是须要先将彩色图像转换为灰度图像. QImage 有一个convertToFormat方法.最開始一直用这个函数来实现. 可是今天细致看了看,发现这个函 ...
- 如何使用 python3 将RGB 图片转换为 灰度图
首先,介绍第一种方法, 使用 PIL 库, PIL库是一种python语言常用的一个图形处理库. 关于 PIL 库的安装本文就不介绍了. from PIL import Image I ...
- Android 将ARGB图片转换为灰度图
思路如下: 1.读取or照相,得到一张ARGB图片. 2.转化为bitmap类,并对其数据做如下操作: A通道保持不变,然后逐像素计算:X = 0.3×R+0.59×G+0.11×B,并使这个像素的值 ...
- C# (灰度)加权平均法将图片转换为灰度图
private Bitmap ToG(string file) { using (Bitmap o = new Bitmap(file)) { Bitmap g = new Bitmap(o.Widt ...
- [Xcode 实际操作]六、媒体与动画-(2)使用图形上下文转换图片为灰度图
目录:[Swift]Xcode实际操作 本文将演示如何将图片转换为灰度图. 在项目导航区,打开视图控制器的代码文件[ViewController.swift] import UIKit class V ...
随机推荐
- HDU 1083 Courses(最大匹配模版题)
题目大意: 一共有N个学生跟P门课程,一个学生可以任意选一 门或多门课,问是否达成: 1.每个学生选的都是不同的课(即不能有两个学生选同一门课) 2.每门课都有一个代表(即P门课都被成功选过 ...
- sql server 修改字段大小
alter table AAA ALTER COLUMN BBBvarchar(100); 这种语法只适合把字段往大了设置, 如果更新的字段大小比实际的要小时,并且数据库已存在比要更新的数据大时, ...
- HDOJ(HDU) 1994 利息计算(简单题目)
Problem Description 为自行解决学费,chx勤工俭学收入10000元以1年定期存入银行,年利率为3.7% .利率 按年计算,表示100元存1年的利息为3.7元.实际上有时提前有时推迟 ...
- cf700A As Fast As Possible
On vacations n pupils decided to go on excursion and gather all together. They need to overcome the ...
- 一个linux下socket编程的例子,client连server
关于socket编程,以下文章写得比较好:http://www.cnblogs.com/xudong-bupt/archive/2013/12/29/3483059.html 1. accept()函 ...
- 《Linear Algebra and Its Applications》-chaper1-向量方程、矩阵方程和线性方程组
向量: 向量的基本运算:向量的运算最基本的一件事情,就是基于它n个分量上进行,即对于两个分量的向量a = <a1,a2>,b = <b1,b2>,有a + b = <a1 ...
- 转:理解Java泛型
JDK 5.0 中增加的泛型类型,是 Java 语言中类型安全的一次重要改进.但是,对于初次使用泛型类型的用户来说,泛型的某些方面看起来可能不容易明白,甚至非常奇怪.在本月的“Java 理论和实践”中 ...
- cocos日记
n/2/2015 ADT E:\All Setup\eclipse_past\Eclipse_plugins_ADT 15/2/2015 配置cocos win32 开发环境 链接:htt ...
- 更改navigationController push和pop界面切换动画
For Push: MainView *nextView=[[MainView alloc] init]; [UIView beginAnimations:nil context:NULL]; [UI ...
- ndroid网络(4):HttpClient必经之路----使用线程安全的单例模式HttpClient,及HttpClient和Application的融合
上文简 单介绍了HttpClient和Tomcat服务器的交互,主角是HttpClient,然后它跟服务器交互有两种方式即get和post.所以这个 HttpClient就类似于电脑上用的浏览器.当我 ...