图像的正交变换---沃尔什——哈达马变换

    
    
    
    
  1. /*************************************************************************
  2. *
  3. * 函数名称:
  4. * WALSH()
  5. *
  6. * 参数:
  7. * double* f - 输入的时域序列
  8. * double* F - 输出的频域序列
  9. * int r - 2的幂数
  10. *
  11. * 返回值:
  12. * BOOL - 成功返回TRUE,否则返回FALSE。
  13. *
  14. * 说明:
  15. * 该函数进行一维快速沃尔什——哈达马变换。
  16. *
  17. ************************************************************************/
  18. void WALSH(double*f,double*F,int r);
  19. /*************************************************************************
  20. *
  21. * 函数名称:
  22. * IWALSH()
  23. *
  24. * 参数:
  25. * double* f - 输入的时域序列
  26. * double* F - 输出的频域序列
  27. * int r - 2的幂数
  28. *
  29. * 返回值:
  30. * BOOL - 成功返回TRUE,否则返回FALSE。
  31. *
  32. * 说明:
  33. * 该函数进行一维快速沃尔什——哈达马逆变换。
  34. *
  35. ************************************************************************/
  36. void IWALSH(double*F,double*f,int r);
  37. /*************************************************************************
  38. *
  39. * 函数名称:
  40. * FreqWALSH()
  41. *
  42. * 参数:
  43. * double* f - 输入的时域序列
  44. * double* F - 输出的频域序列
  45. * LONG width - 图象宽度
  46. * LONG height - 图象高度
  47. *
  48. * 返回值:
  49. * BOOL - 成功返回TRUE,否则返回FALSE。
  50. *
  51. * 说明:
  52. * 该函数进行二维快速沃尔什——哈达玛变换。
  53. *
  54. ************************************************************************/
  55. BOOL FreqWALSH(double*f,double*F, LONG width, LONG height);
  56. /*************************************************************************
  57. *
  58. * 函数名称:
  59. * IFreqWALSH()
  60. *
  61. * 参数:
  62. * double* f - 输入的时域序列
  63. * double* F - 输出的频域序列
  64. * LONG width - 图象宽度
  65. * LONG height - 图象高度
  66. *
  67. * 返回值:
  68. * BOOL - 成功返回TRUE,否则返回FALSE。
  69. *
  70. * 说明:
  71. * 该函数进行二维快速沃尔什——哈达玛逆变换。
  72. *
  73. ************************************************************************/
  74. BOOL IFreqWALSH(double*f,double*F, LONG width, LONG height);
  75. /*************************************************************************
  76. *
  77. * 函数名称:
  78. * BmpWalsh()
  79. *
  80. * 参数:
  81. * BYTE* bmp,LONG width,LONG height
  82. *
  83. * 返回值:
  84. * BOOL - 成功返回TRUE,否则返回FALSE。
  85. *
  86. * 说明:
  87. * 该函数对图象进行二维快速沃尔什——哈达马变换。
  88. *
  89. ************************************************************************/
  90. BOOL BmpWalsh(BYTE* bmp,LONG width,LONG height);
     
     
     
     
  1. voidMyProcess::WALSH(double*f,double*F,int r)
  2. {
  3. // 循环变量
  4. LONG i;
  5. LONG j;
  6. LONG k;
  7. // 中间变量
  8. int p;
  9. double* X;
  10. // 计算快速沃尔什变换点数
  11. LONG N =1<< r;
  12. // 分配运算所需的数组
  13. double* X1 =newdouble[N];
  14. double* X2 =newdouble[N];
  15. // 将时域点写入数组X1
  16. memcpy(X1, f,sizeof(double)* N);
  17. // 蝶形运算
  18. for(k =0; k < r; k++)
  19. {
  20. for(j =0; j <1<<k; j++)
  21. {
  22. for(i =0; i <1<<(r - k -1); i++)
  23. {
  24. p = j *(1<<(r - k));
  25. X2[i + p]= X1[i + p]+ X1[i + p +(int)(1<<(r - k -1))];
  26. X2[i + p +(int)(1<<(r - k -1))]= X1[i + p]- X1[i + p +(int)(1<<(r - k -1))];
  27. }
  28. }
  29. // 互换X1和X2
  30. X = X1;
  31. X1 = X2;
  32. X2 = X;
  33. }
  34. // 调整系数
  35. for(j =0; j < N; j++)
  36. {
  37. p =0;
  38. for(i =0; i < r; i++)
  39. {
  40. if(j &(1<<i))
  41. {
  42. p +=1<<(r - i -1);
  43. }
  44. }
  45. F[j]= X1[p]/ N;
  46. }
  47. // 释放内存
  48. delete X1;
  49. delete X2;
  50. }
  51. voidMyProcess::IWALSH(double*F,double*f,int r)
  52. {
  53. // 循环变量
  54. int i;
  55. // 计算变换点数
  56. LONG N =1<< r;
  57. // 调用快速沃尔什-哈达玛变换进行反变换
  58. WALSH(F, f, r);
  59. // 调整系数
  60. for(i =0; i < N; i++)
  61. f[i]*= N;
  62. }
  63. BOOL MyProcess::FreqWALSH(double*f,double*F, LONG width, LONG height)
  64. {
  65. // 循环变量
  66. LONG i;
  67. LONG j;
  68. LONG k;
  69. // 进行离散余弦变换的宽度和高度(2的整数次方)
  70. LONG w =1;
  71. LONG h =1;
  72. int wp =0;
  73. int hp =0;
  74. // 计算进行离散余弦变换的宽度和高度(2的整数次方)
  75. while(w < width/3)
  76. {
  77. w *=2;
  78. wp++;
  79. }
  80. while(h < height)
  81. {
  82. h *=2;
  83. hp++;
  84. }
  85. // 分配内存
  86. double*TempIn=newdouble[h];
  87. double*TempOut=newdouble[h];
  88. // 对y方向进行离散余弦变换
  89. for(i =0; i < w *3; i++)
  90. {
  91. // 抽取数据
  92. for(j =0; j < h; j++)
  93. TempIn[j]= f[j * w *3+ i];
  94. // 一维快速离散余弦变换
  95. WALSH(TempIn,TempOut, hp);
  96. // 保存变换结果
  97. for(j =0; j < h; j++)
  98. f[j * w *3+ i]=TempOut[j];
  99. }
  100. // 释放内存
  101. deleteTempIn;
  102. deleteTempOut;
  103. // 分配内存
  104. TempIn=newdouble[w];
  105. TempOut=newdouble[w];
  106. // 对x方向进行快速离散余弦变换
  107. for(i =0; i < h; i++)
  108. {
  109. for(k =0; k <3; k++)
  110. {
  111. // 抽取数据
  112. for(j =0; j < w; j++)
  113. TempIn[j]= f[i * w *3+ j *3+ k];
  114. // 一维快速离散余弦变换
  115. WALSH(TempIn,TempOut, wp);
  116. // 保存变换结果
  117. for(j =0; j < w; j++)
  118. F[i * w *3+ j *3+ k]=TempOut[j];
  119. }
  120. }
  121. // 释放内存
  122. deleteTempIn;
  123. deleteTempOut;
  124. return TRUE;
  125. }
  126. BOOL MyProcess::IFreqWALSH(double*f,double*F, LONG width, LONG height)
  127. {
  128. // 循环变量
  129. LONG i;
  130. LONG j;
  131. LONG k;
  132. // 赋初值
  133. LONG w =1;
  134. LONG h =1;
  135. int wp =0;
  136. int hp =0;
  137. // 计算进行付立叶变换的宽度和高度(2的整数次方)
  138. while(w < width/3)
  139. {
  140. w *=2;
  141. wp++;
  142. }
  143. while(h < height)
  144. {
  145. h *=2;
  146. hp++;
  147. }
  148. // 分配内存
  149. double*TempIn=newdouble[w];
  150. double*TempOut=newdouble[w];
  151. // 对x方向进行快速付立叶变换
  152. for(i =0; i < h; i++)
  153. {
  154. for(k =0; k <3; k++)
  155. {
  156. // 抽取数据
  157. for(j =0; j < w; j++)
  158. TempIn[j]= F[i * w *3+ j *3+ k];
  159. // 一维快速傅立叶变换
  160. IWALSH(TempIn,TempOut, wp);
  161. // 保存变换结果
  162. for(j =0; j < w; j++)
  163. F[i * w *3+ j *3+ k]=TempOut[j];
  164. }
  165. }
  166. // 释放内存
  167. deleteTempIn;
  168. deleteTempOut;
  169. TempIn=newdouble[h];
  170. TempOut=newdouble[h];
  171. // 对y方向进行快速付立叶变换
  172. for(i =0; i < w *3; i++)
  173. {
  174. // 抽取数据
  175. for(j =0; j < h; j++)
  176. TempIn[j]= F[j * w *3+ i];
  177. // 一维快速傅立叶变换
  178. IWALSH(TempIn,TempOut, hp);
  179. // 保存变换结果
  180. for(j =0; j < h; j++)
  181. F[j * w *3+ i]=TempOut[j];
  182. }
  183. // 释放内存
  184. deleteTempIn;
  185. deleteTempOut;
  186. for(i =0; i < h; i++)
  187. {
  188. for(j =0; j < w *3; j++)
  189. {
  190. if(i < height && j < width)
  191. *(f + i * width + j)= F[i * w *3+ j];
  192. }
  193. }
  194. return TRUE;
  195. }
  196. BOOL MyProcess::BmpWalsh(BYTE* bmp,LONG width,LONG height)
  197. {
  198. // 循环变量
  199. LONG i;
  200. LONG j;
  201. // 进行沃尔什——哈达玛变换的宽度和高度(2的整数次方)
  202. LONG w =1;
  203. LONG h =1;
  204. int wp =0;
  205. int hp =0;
  206. // 计算进行离散余弦变换的宽度和高度(2的整数次方)
  207. while(w < width/3)
  208. {
  209. w *=2;
  210. wp++;
  211. }
  212. while(h < height)
  213. {
  214. h *=2;
  215. hp++;
  216. }
  217. // 分配内存
  218. double*f =newdouble[w * h *3];
  219. double*F =newdouble[w * h *3];
  220. // 向时域赋值并补零
  221. for(i =0; i < h; i++)
  222. {
  223. for(j =0; j < w *3; j++)
  224. {
  225. if(i < height && j < width)
  226. f[i * w *3+ j]= bmp[width * i + j];
  227. else
  228. f[w * i *3+ j]=0.0f;
  229. }
  230. }
  231. // 进行频谱分析
  232. if(FreqWALSH(f, F,width, height)== FALSE)
  233. return FALSE;
  234. // 更新所有象素
  235. for(i =0; i < height; i++)
  236. {
  237. for(j =0; j < width; j++)
  238. {
  239. // 判断是否超过255
  240. if(fabs(F[i * w *3+ j]*1000)>255)
  241. {
  242. // 对于超过的,直接设置为255
  243. bmp[width *(height -1- i)+ j]=255;
  244. }
  245. else
  246. {
  247. // 如果没有超过,则按实际计算结果赋值
  248. bmp[width *(height -1- i)+ j]= fabs(F[i * w *3+ j]*1000);
  249. }
  250. }
  251. }
  252. //释放内存
  253. delete[] f;
  254. delete[] F;
  255. // 返回
  256. return TRUE;
  257. }

你可能感兴趣的:(图像处理)