数字图像处理基础作业

合集下载
  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。

1.图像均值化
2.图像的Gauss低通和Gauss高通
3.对图像进行Gamma变化
4.DCT变换,加上量化在反量化,和IDCT
这四个题目,如果是对一些进行图像处理的程序员来讲或者很简单,但是我基本不接触图像处理这个方面的(虽然我头上挂着这个牌子),基本原理不同,很难写程序。

不过幸好我同学是搞这个方面的,而且他的讲解能让我很快的知道我应该怎么去处理这个图像,而且通过网络的搜索,我发现wiki上的讲解真的相当的精准阿...不带让人纠结的数学公式,也不会长篇大论,有的就是通俗易懂的步骤和例子。

让人很快能知道我应该怎么都作就能完成这个效果的处理。

这是我一直很喜欢使用wiki的原因,推荐推荐阿....
对于这个作业我本打算以最大的速度做完的,也不想真的去对原理进行真正的了解!所以只要知道怎么去做就可以了。

突然想到了那几天前我好像也学习QT,所以想连着这个一起作一次练习。

qt一个gui做的不错的库!而且简单的很...
既然使用了QT那就要求我使用C++来写这个程序,C++这个语言,很久很久没使用了,主要是觉得自己对C++好像很陌生了,或者可以说是对面向对象这个思想的陌生。

关于这点,我也很想提出我的一点点想法。

虽然很早就开始使用面向对象去编程,可是好像自己一直没有入门面向对象这种思想。

使用C++的过程好像是将C++当成C来使用,很少很少说一定要使用到类,继承,多态这种特性。

看了很多书说,要学好C++就要放弃一些东西,把面向对象的这些东西学好。

可是面向对象到底是一种什么样的思想呢,有的时候很想用面向对象的思想去写程序,可是有时候却发现自己好像是为了面向对象而面向对象...好似纠结....应该是我经历的还不够吧。

关于这个作业,我最想讲的两个方面是:
1.qt中的QImage这个对象,为了能让内存高效的访问,qt通过空间去换取时间的方法来提升效率。

让每一行都能被4B整除,这就是让qt本身会对每一行进行填充的过程,所以将一个一维的图像数据的转换为QImage是一个要小心的过程。

当然其实如果你懂的,那就是一个构造函数的问题,我在这方面犯过错,所以提出来了。

2.关于DCT的变换
这个变换的公式很长很复杂,如果按公式来做的话,这个计算量是很大的,所以在网络搜索到一篇论文,好像是通过将其变为矩阵的乘法的运算,能减少相当大的运算量。

据说JPEG 也是用这种方式进行dct的变化的。

使用矩阵的运算简单很多,而且很多东西是很巧妙的联系着的。

关于dct应该是我花时间最多的一个方面,因为开始不懂是怎么样的过程,随便看了以下就开始写程序,最后不但程序有问题,连我改程序的心情都没有了。

直接把那个程序del了,重新写。

在写之前找了不少的论文和资料,在有很大把握了基础下,开始了编码的过程,那
天花了5个小时才完成,最后还有一点点的暇眦,不过那个时候时间太晚了,坚持不住就去睡觉了。

第二天花了点时间调试以后,很顺利的完成了,而且变化的速度很快,比我使用公式法快很多。

而且效果很好的样子..让我很开心,这种成功的感觉很久没有了。

我只想把最好的那部分代码贴出来给大家看,DCT变换:
当然如果大家需要这个运行的代码可以发email给我(smy19890720@),哈哈很多的bug我可不管的哦....
[cpp]view plaincopyprint?
1. void pimage::rgb_convert_yuv()
2. {
3. for(size_t j = 0; j < heigth8; j++)
4. {
5. for(size_t i = 0; i < width8; i++)
6. {
7. if(j < heigth && i < width)
8. {
9. int r = image[j*width*bpp+i*bpp + 2];
10. int g = image[j*width*bpp+i*bpp + 1];
11. int b = image[j*width*bpp+i*bpp];
12. y[j][i] = 0.3 * r + g * 0.59 + b * 0.11;
13. u[j][i] = -0.147 *r - 0.289 * g + 0.436 * b;
14. v[j][i] = 0.615 * r - 0.515 * g - 0.100 * b;
15. y[j][i] = y[j][i] - 128;
16.
17. //printf("r = %u,g = %u,b = %u\n",r,g,b);
18. //printf("y = %d,u = %d,v = %d\n",y[j][i],u[j][i],v[j][i]);
19. }
20. else
21. {
22. y[j][i] = 0;
23. u[j][i] = 0;
24. v[j][i] = 0;
25. }
26. }
27. }
28. }
29.
30. v oid pimage::yuv_convert_rgb()
31. {
32. for(size_t i = 0; i < heigth8; i++)
33. { for(size_t j = 0; j < width8; j++) {
34. if(i < heigth && j < width)
35. {
36. int tmpy = y[i][j] + 128;
37. int tmpu = u[i][j];
38. int tmpv = v[i][j];
39.
40. int r = tmpy + (1.13983 * (tmpv));
41. int g = tmpy - (0.58 * (tmpv)) - (0.39 *(tmpu));
42. int b = tmpy + (2.03211 * (tmpu));
43. if(r > 255)
44. r = 255;
45. if(g > 255)
46. g = 255;
47. if(b > 255)
48. b = 255;
49.
50. if(r < 0)
51. r = 0;
52. if(g < 0)
53. g = 0;
54. if(b < 0)
55. b = 0;
56.
57. //printf("r = %d,g = %d,b = %d\n",r,g,b);
58. //printf("y = %d,u = %d,v = %d\n",tmpy,tmpu,tmpv);
59.
60.
61. image[i*width*bpp+j*bpp] = b;
62. image[i*width*bpp+j*bpp + 1] = g;
63. image[i*width*bpp+j*bpp + 2] = r;
64. }
65. }
66. }
67. }
68.
69. v oid pimage::DCT()
70. {
71. int tmpy[8][8];
72. int tmpu[8][8];
73. int tmpv[8][8];
74.
75. rgb_convert_yuv();
76. get_dct(dct,dct_t);
77.
78. for(int j = 0; j < heigth8/8; j++)
79. {
80. for(int i = 0; i < width8/8; i++)
81. {
82. for(int h = 0; h < 8; h++)
83. {
84. for(int w = 0; w < 8; w++)
85. {
86. tmpy[h][w] = y[j*8+h][i*8+w];
87. tmpu[h][w] = u[j*8+h][i*8+w];
88. tmpv[h][w] = v[j*8+h][i*8+w];
89. //printf("j = %d,i = %d,h = %d,w = %d\n",j,i,h,w);
90. }
91. }
92.
93. matrix_mul(dct,tmpy,dct_t);
94. matrix_mul(dct,tmpu,dct_t);
95. matrix_mul(dct,tmpv,dct_t);
96.
97. lianhuay(tmpy);
98. lianhuau(tmpu);
99. lianhuau(tmpv);
100. for(int h = 0; h < 8; h++) 101. {
102. for(int w = 0; w < 8; w++) 103. {
104. y[j*8+h][i*8+w] = tmpy[h][w]; 105. u[j*8+h][i*8+w] = tmpu[h][w]; 106. v[j*8+h][i*8+w] = tmpv[h][w]; 107. }
108.
109. }
110. }
111. }
112. }
113.
114. void pimage::IDCT()
115. {
116. int tmpy[8][8];
117. int tmpu[8][8];
118. int tmpv[8][8];
119.
120.
121. for(int j = 0; j < heigth8/8; j++) 122. {
123. for(int i = 0; i < width8/8; i++) 124. {
125. for(int h = 0; h < 8; h++) 126. {
127. for(int w = 0; w < 8; w++) 128. {
129. tmpy[h][w] = y[j*8+h][i*8+w]; 130. tmpu[h][w] = u[j*8+h][i*8+w]; 131. tmpv[h][w] = v[j*8+h][i*8+w]; 132. }
133. }
134.
135. ilianhuay(tmpy);
136. ilianhuau(tmpu);
137. ilianhuau(tmpv);
138.
139. matrix_mul(dct_t,tmpy,dct);
140. matrix_mul(dct_t,tmpu,dct);
141. matrix_mul(dct_t,tmpv,dct);
142.
143. for(int h = 0; h < 8; h++)
144. {
145. for(int w = 0; w < 8; w++)
146. {
147. y[j*8+h][i*8+w] = tmpy[h][w];
148. u[j*8+h][i*8+w] = tmpu[h][w];
149. v[j*8+h][i*8+w] = tmpv[h][w];
150. }
151. }
152.
153. }
154. }
155. yuv_convert_rgb();
156. }
157. void pimage::get_dct(float (*dct)[8],float (*dct_T)[8]) 158. {
159. for(int i = 0; i < 8; i++)
160. {
161. dct[0][i] = 1.0 / sqrt(8);
162. dct_T[i][0] = dct[0][i];
163. }
164.
165. for(int i = 1; i < 8; i++)
166. for(int j = 0; j < 8; j++)
167. {
168. dct[i][j] = sqrt(2.0/8)*cos((2*j+1)*i*PI/(2.0*8));
169. dct_T[j][i] = dct[i][j];
170. }
171. }
172.
173. void pimage::matrix_mul(float (*first)[8],int (*sec)[8],float (*third)[8]) 174. {
175. float tmp[8][8];
176. float tmp1[8][8];
177.
178. for(int i = 0;i < 8;i++)
179. {
180. for(int j = 0;j < 8;j++)
181. {
182. tmp[i][j] = 0;
183. for(int k = 0;k < 8;k++)
184. {
185. tmp[i][j] += (first[i][k] * sec[k][j]);
186. }
187. }
188. }
189.
190. for(int i = 0;i < 8; i++)
191. {
192. for(int j = 0;j < 8; j++)
193. {
194. tmp1[i][j] = 0;
195. for(int k = 0; k < 8;k++)
196. {
197. tmp1[i][j] += (tmp[i][k] * third[k][j]);
198. }
199. }
200. }
201.
202. for(int i = 0;i < 8;i++)
203. {
204. for(int j = 0;j < 8;j++)
205. {
206. sec[i][j] = round(tmp1[i][j]); 207. }
208. }
209. }
210.
211. int pimage::round(float thiz) 212. {
213. if(fabs(thiz - (int)thiz) >= (1.0/2)) 214. {
215. if(thiz > 0)
216. {
217. return (int)thiz + 1;
218. }
219. else
220. {
221. return (int)thiz - 1;
222. }
223. }
224. else
225. {
226. return (int)thiz;
227. }
228. }
229.
230.
231. void pimage::lianhuay(int (*thiz)[8]) 232. {
233. static int matrix[8][8] = {
234. {16,11,10,16,24,40,51,61}, 235. {12,12,14,19,26,58,60,55}, 236. {14,13,16,24,40,57,69,56}, 237. {14,17,22,29,51,87,80,62},
238. {18,22,37,56,68,109,103,77},
239. {24,35,55,64,81,104,113,92},
240. {49,64,78,87,103,121,120,101},
241. {72,92,95,98,112,100,103,99},
242. };
243.
244. for(int i = 0; i < 8; i++)
245. {
246. for(int j = 0; j < 8; j++)
247. {
248. thiz[i][j] = round(thiz[i][j]*1.0/matrix[i][j]); 249. }
250. }
251. }
252.
253. void pimage::ilianhuay(int (*thiz)[8])
254. {
255. static int matrix[8][8] = {
256. {16,11,10,16,24,40,51,61},
257. {12,12,14,19,26,58,60,55},
258. {14,13,16,24,40,57,69,56},
259. {14,17,22,29,51,87,80,62},
260. {18,22,37,56,68,109,103,77},
261. {24,35,55,64,81,104,113,92},
262. {49,64,78,87,103,121,120,101},
263. {72,92,95,98,112,100,103,99},
264. };
265.
266. for(int i = 0; i < 8; i++)
267. {
268. for(int j = 0; j < 8; j++)
269. {
270. thiz[i][j] = thiz[i][j] * matrix[i][j];
271. }
272. }
273. }
274.
275. void pimage::lianhuau(int (*thiz)[8])
276. {
277. static int matrix[8][8] = {
278. {17,18,24,47,99,99,99,99},
279. {18,21,26,66,99,99,99,99},
280. {24,26,56,99,99,99,99,99},
281. {47,66,99,99,99,99,99,99},
282. {99,99,99,99,99,99,99,99},
283. {99,99,99,99,99,99,99,99},
284. {99,99,99,99,99,99,99,99},
285. {99,99,99,99,99,99,99,99},
286. };
287.
288. for(int i = 0; i < 8; i++)
289. {
290. for(int j = 0; j < 8; j++)
291. {
292. thiz[i][j] = round(thiz[i][j]*1.0/matrix[i][j]); 293. }
294. }
295. }
296.
297. void pimage::ilianhuau(int (*thiz)[8])
298. {
299. static int matrix[8][8] = {
300. {17,18,24,47,99,99,99,99},
301. {18,21,26,66,99,99,99,99},
302. {24,26,56,99,99,99,99,99},
303. {47,66,99,99,99,99,99,99},
304. {99,99,99,99,99,99,99,99},
305. {99,99,99,99,99,99,99,99},
306. {99,99,99,99,99,99,99,99},
307. {99,99,99,99,99,99,99,99},
308. };
309.
310. for(int i = 0; i < 8; i++)
311. {
312. for(int j = 0; j < 8; j++)
313. {
314. thiz[i][j] = thiz[i][j] * matrix[i][j];
315. }
316. }
317. }
318.
319. void pimage::get_psnr()
320. {
321. uchar *tmp_image = (uchar*)calloc(width*heigth*bpp,sizeof(uchar)); 322. memcpy(tmp_image,image,width*heigth*bpp);
323. DCT();
324. IDCT();
325.
326. double psnr_r = 0;
327. double psnr_g = 0;
328. double psnr_b = 0;
329.
330. double mse_r = 0;
331. double mse_g = 0;
332. double mse_b = 0;
333.
334. for(int i = 0; i < this->heigth; i++)
335. for(int j = 0; j < this->width; j++)
336. {
337. mse_b = mse_b + (image[i*this->width*bpp+j*bpp] - tmp_image[i* width*bpp+j*bpp]) * (image[i*this->width*bpp+j*bpp] - tmp_image[i*width*b pp+j*bpp]);
338. mse_g = mse_g + (image[i*this->width*bpp+j*bpp + 1] - tmp_imag e[i*width*bpp+j*bpp + 1]) * (image[i*this->width*bpp+j*bpp + 1] - tmp_imag e[i*width*bpp+j*bpp + 1]);
339. mse_r = mse_r + (image[i*this->width*bpp+j*bpp + 2] - tmp_image [i*width*bpp+j*bpp + 2]) * (image[i*this->width*bpp+j*bpp + 2] - tmp_image[
i*width*bpp+j*bpp + 2]);
340. }
341. mse_r = mse_r / (heigth * width);
342. mse_g = mse_g / (heigth * width);
343. mse_b = mse_b / (heigth * width);
344.
345. psnr_r = 20 * log10(255/sqrt(mse_r));
346. psnr_g = 20 * log10(255/sqrt(mse_g));
347. psnr_b = 20 * log10(255/sqrt(mse_b));
348.
349. printf("r = %lf,g = %lf,b = %lf\n",psnr_r,psnr_g,psnr_b);
350. free(tmp_image);
351. }。

相关文档
最新文档