OpenCV实现基于8*8块DCT变换的图像压缩

来源:互联网 发布:360防止蹭网软件 编辑:程序博客网 时间:2024/05/21 10:46

这几天一直在看MPEG编解码的原理,由于利用ffmpeg实在提不出DCT系数,就根据MPEG的编码原理来看看这个DCT系数到底什么样,于是在OpenCV中实现了一下图像压缩这一块,基于8*8块DCT变换,同时也再进行了一下反变换,最后得到了原图。

代码如下:

#include "highgui.h"#include <cv.h>#include<iostream>using namespace std;using namespace cv;int main(){Mat img = imread("1.jpg");//分解为YUV颜色空间Mat YUVImage;cvtColor(img,YUVImage,CV_BGR2YUV);//分解为三个通道vector<Mat> YUV;split(YUVImage,YUV);//先转换下格式Mat float_Y,float_U,float_V;YUV[0].convertTo(float_Y,CV_64FC1);YUV[1].convertTo(float_U,CV_64FC1);YUV[2].convertTo(float_V,CV_64FC1);   //基于8*8块的DCT变换及其反变换Rect windows; //利用这个8*8的矩形来进行8*8块的DCT变换//DCT变换Mat DCTU,DCTV,DCTY;float_Y.copyTo(DCTY);float_U.copyTo(DCTU);float_V.copyTo(DCTV);for (int i = 0;i<img.cols/8;i++){for (int j = 0;j<img.rows/8;j++){windows.x = 8 * i;windows.y = 8 * j;windows.height = 8;windows.width = 8;dct(float_Y(windows),DCTY(windows));dct(float_U(windows),DCTU(windows));dct(float_V(windows),DCTV(windows));}}////反DCT变换for (int i = 0;i<img.cols/8;i++){for (int j = 0;j<img.rows/8;j++){windows.x = 8 * i;windows.y = 8 * j;windows.height = 8;windows.width = 8;dct(DCTY(windows),float_Y(windows),DCT_INVERSE);dct(DCTU(windows),float_U(windows),DCT_INVERSE);dct(DCTV(windows),float_V(windows),DCT_INVERSE);}}vector<Mat> YUV_dst(3);//格式转换float_Y.convertTo(YUV_dst[0],CV_8UC1);float_U.convertTo(YUV_dst[1],CV_8UC1);float_V.convertTo(YUV_dst[2],CV_8UC1);//将三个通道进行合并Mat yuv,dst_RGB;merge(YUV_dst,yuv);//转为RGB图像cvtColor(yuv,dst_RGB,CV_YUV2BGR);imshow("Y",DCTY);imshow("U",DCTU);imshow("V",DCTV);imshow("dst",dst_RGB);waitKey(0);system("pause");}


0 0
原创粉丝点击