#include "stdafx.h" #include "waveReconstruct.h" // 功能:函数 idwt() 对输入的小波分解系数进行逆离散小波变换,重构出信号序列dst bool idwt(cv::Mat &dst, const cv::Mat &cA, const cv::Mat &cD, const cv::Mat &LF, const cv::Mat &HF) { // 输入向量有效性判断:只处理行向量 if (cA.empty() == true || (cA.type() != CV_64FC1)) { return false; } if (cD.empty() == true || (cD.type() != CV_64FC1)) { return false; } if (cA.size != cD.size || cA.type() != cD.type() || cA.rows != 1) { return false; } // 滤波器有效性判断 if (LF.empty() == true || LF.type() != CV_64FC1 || HF.empty() == true || HF.type() != CV_64FC1 || LF.size != HF.size || LF.rows != 1) { return false; } // (1)低频 // (1.1) 上采样 + 赋值 cv::Mat upl = cv::Mat(1, 2 * cA.cols + 1, cA.type()); upl = cv::Scalar(0.0, 0.0, 0.0); for (int i = 0; i < cA.cols; i++) { upl.at(0, 2 * i + 1) = cA.at(0, i); } // (1.2) 卷积 cv::Mat cvl = cv::Mat(1, upl.cols + LF.cols - 1, cA.type()); cvl = cv::Scalar(0.0, 0.0, 0.0); // 理论:数字信号卷积公式 for (int i = 0; i < cvl.cols; i++) { for (int j = 0; j < LF.cols; j++) { if ((i - j) >= 0 && (i - j) < upl.cols) { cvl.at(0, i) += LF.at(0,j) * upl.at(0, i - j); } } } // (2) 高频 // (2.1) 上采样+赋值 cv::Mat uph = cv::Mat(1, 2 * cD.cols + 1, cA.type()); uph = cv::Scalar(0.0, 0.0, 0.0); for (int i = 0; i < cD.cols; i++) { uph.at(0, 2 * i + 1) = cD.at(0, i); } // (2.2) 卷积 cv::Mat cvh = cv::Mat(1, uph.cols + HF.cols - 1, cD.type()); cvh = cv::Scalar(0.0, 0.0, 0.0); for (int i = 0; i < cvh.cols; i++) { for (int j = 0; j < HF.cols; j++) { if ((i - j) >= 0 && (i - j) < uph.cols) { cvh.at(0, i) += HF.at(0,j) * uph.at(0, i - j); } } } // 获得结果 dst = cvl + cvh; return true; } // 功能:函数 idwt2() 对输入的子矩阵序列进行逆小波变换, 得到重构矩阵outcA bool idwt2(cv::Mat &outcA, const cv::Mat &rcA, const cv::Mat &rcV, const cv::Mat &rcH, const cv::Mat &rcD, const cv::Mat &Lo_R, const cv::Mat &Hi_R, cv::Vec2i size) { // 子系数矩阵空值、类型判断 if (rcA.empty() == true || (rcA.type() != CV_64FC1)) { return false; } if (rcV.empty() == true || (rcV.type() != CV_64FC1)) { return false; } if (rcH.empty() == true || (rcH.type() != CV_64FC1)) { return false; } if (rcD.empty() == true || (rcD.type() != CV_64FC1)) { return false; } // 子系数矩阵类型一致性判断 if (rcA.type() != rcV.type() || rcA.type() != rcH.type() || rcA.type() != rcD.type() || rcV.type() != rcH.type() || rcV.type() != rcD.type() || rcH.type() != rcD.type()) { return false; } // 子系数矩阵尺寸一致性判断 if (rcA.size() != rcV.size() || rcA.size() != rcH.size() || rcA.size() != rcD.size() || rcV.size() != rcH.size() || rcV.size() != rcD.size() || rcH.size() != rcD.size()) { return false; } // 滤波器:空值、类型、尺寸判断 if (Lo_R.empty() == true || Lo_R.type() != CV_64FC1) { return false; } if (Hi_R.empty() == true || Hi_R.type() != CV_64FC1) { return false; } if (Lo_R.size() != Hi_R.size()) { return false; } // 本级小波分解系数矩阵的大小 if (size[0] <= 0 || size[1] <= 0) { return false; } // 步骤1:先将四个子序列合成一个矩阵 cv::Mat tmp_mat = cv::Mat(2 * rcA.rows, 2 * rcA.cols, rcA.type()); tmp_mat = cv::Scalar(0.0, 0.0, 0.0); rcA.copyTo(tmp_mat(cv::Range(0, rcA.rows), cv::Range(0, rcA.cols))); rcV.copyTo(tmp_mat(cv::Range(0, rcA.rows), cv::Range(rcA.cols, 2 * rcA.cols))); rcH.copyTo(tmp_mat(cv::Range(rcA.rows, 2 * rcA.rows), cv::Range(0, rcA.cols))); rcD.copyTo(tmp_mat(cv::Range(rcA.rows, 2 * rcA.rows), cv::Range(rcA.cols, 2 * rcA.cols))); // 步骤2:逐列逆变换结果, 变换结果行数裁剪为:size[0] cv::Mat tmp_mat_cR = cv::Mat(size[0], 2 * rcA.cols, rcA.type()); // 逐列逆变换 for (int i = 0; i < tmp_mat.cols; i++) { cv::Mat ca1 = tmp_mat(cv::Range(0, rcA.rows), cv::Range(i, i + 1)); // 第i列上半部分 cv::Mat cd1 = tmp_mat(cv::Range(rcA.rows, rcA.rows * 2), cv::Range(i, i + 1)); // 第i列下半部分 // 转为行向量 cv::transpose(ca1, ca1); cv::transpose(cd1, cd1); // 一维小波逆变换 cv::Mat tmp1; bool ret = idwt(tmp1, // 输出 ca1, cd1, Lo_R, Hi_R);// 输入 if (ret == false) { return false; } else { cv::transpose(tmp1, tmp1); // 转置为列向量 // 取中间部分 int begin = (tmp1.rows - size[0]) / 2; int end = begin + size[0]; // 判断begin end 越界情况 if (begin >= 0 && end <= tmp1.rows) { tmp1 = tmp1(cv::Range(begin, end), cv::Range(0, 1)); tmp1.copyTo(tmp_mat_cR(cv::Range(0, size[0]), cv::Range(i, i + 1))); } else { return false; } } } // 步骤3:逐行逆变换结果,变换结果列数裁剪为:size[1] cv::Mat tmp_mat_cR_rR = cv::Mat(size[0], size[1], rcA.type()); for (int i = 0; i < size[0]; i++) { cv::Mat ca2 = tmp_mat_cR(cv::Range(i, i + 1), cv::Range(0, rcA.cols)); cv::Mat cd2 = tmp_mat_cR(cv::Range(i, i + 1), cv::Range(rcA.cols, rcA.cols * 2)); // 一维小波逆变换 cv::Mat tmp2; bool ret = idwt(tmp2, // 输出 ca2, cd2, Lo_R, Hi_R); // 输入 if (ret == false) { return false; } else { int begin = (tmp2.cols - size[1]) / 2; int end = begin + size[1]; if (begin >= 0 && end <= tmp2.cols) { // 取中间部分 tmp2 = tmp2(cv::Range(0, 1), cv::Range(begin, end)); tmp2.copyTo(tmp_mat_cR_rR(cv::Range(i, i + 1), cv::Range(0, size[1]))); } else { return false; } } } // 得到结果 tmp_mat_cR_rR.copyTo(outcA); return true; } // 功能:函数 getWaveRecFilter() 基于小波名称wname计算小波重构滤波器 bool getWaveRecFilter(cv::Mat &Lo_R, cv::Mat &Hi_R, const string wname) { if (wname == "") { return false; } // haar小波 if (wname == "haar") { // 创建Lo_D Lo_R = cv::Mat(1, 2, CV_64FC1); Lo_R.at(0, 0) = 0.7071; Lo_R.at(0, 1) = 0.7071; // 创建Hi_D Hi_R = cv::Mat(1, 2, CV_64FC1); Hi_R.at(0, 0) = 0.7071; Hi_R.at(0, 1) = -0.7071; } else if (wname == "sym1") { // 创建Lo_D Lo_R = cv::Mat(1, 2, CV_64FC1); Lo_R.at(0, 0) = 0.7071; Lo_R.at(0, 1) = 0.7071; // 创建Hi_D Hi_R = cv::Mat(1, 2, CV_64FC1); Hi_R.at(0, 0) = 0.7071; Hi_R.at(0, 1) = -0.7071; } else if (wname == "sym2") { // 创建Lo_D Lo_R = cv::Mat(1, 4, CV_64FC1); Lo_R.at(0, 0) = 0.4830 ; Lo_R.at(0, 1) = 0.8365 ; Lo_R.at(0, 2) = 0.2241 ; Lo_R.at(0, 3) = -0.1294; // 创建Hi_D Hi_R = cv::Mat(1, 4, CV_64FC1); Hi_R.at(0, 0) = -0.1294; Hi_R.at(0, 1) = -0.2241; Hi_R.at(0, 2) = 0.8365 ; Hi_R.at(0, 3) = -0.4830; } else if (wname == "sym3") { // 创建Lo_D Lo_R = cv::Mat(1, 6, CV_64FC1); Lo_R.at(0, 0) = 0.3327 ; Lo_R.at(0, 1) = 0.8069 ; Lo_R.at(0, 2) = 0.4599 ; Lo_R.at(0, 3) = -0.1350; Lo_R.at(0, 4) = -0.0854; Lo_R.at(0, 5) = 0.0352; // 创建Hi_D Hi_R = cv::Mat(1, 6, CV_64FC1) ; Hi_R.at(0, 0) = 0.0352 ; Hi_R.at(0, 1) = 0.0854 ; Hi_R.at(0, 2) = -0.1350; Hi_R.at(0, 3) = -0.4599; Hi_R.at(0, 4) = 0.8069 ; Hi_R.at(0, 5) = -0.3327; } else if (wname == "sym4") { // 创建Lo_D Lo_R = cv::Mat(1, 8, CV_64FC1); Lo_R.at(0, 0) = 0.0322 ; Lo_R.at(0, 1) = -0.0126; Lo_R.at(0, 2) = -0.0992; Lo_R.at(0, 3) = 0.2979 ; Lo_R.at(0, 4) = 0.8037 ; Lo_R.at(0, 5) = 0.4976 ; Lo_R.at(0, 6) = -0.0296; Lo_R.at(0, 7) = -0.0758; // 创建Hi_D Hi_R = cv::Mat(1, 8, CV_64FC1); Hi_R.at(0, 0) = -0.0758; Hi_R.at(0, 1) = 0.0296 ; Hi_R.at(0, 2) = 0.4976 ; Hi_R.at(0, 3) = -0.8037; Hi_R.at(0, 4) = 0.2979 ; Hi_R.at(0, 5) = 0.0992 ; Hi_R.at(0, 6) = -0.0126; Hi_R.at(0, 7) = -0.0322; } else if (wname == "sym5") { // 创建Lo_D Lo_R = cv::Mat(1, 10, CV_64FC1); Lo_R.at(0, 0) = 0.0195 ; Lo_R.at(0, 1) = -0.0211; Lo_R.at(0, 2) = -0.1753; Lo_R.at(0, 3) = 0.0166 ; Lo_R.at(0, 4) = 0.6340 ; Lo_R.at(0, 5) = 0.7234 ; Lo_R.at(0, 6) = 0.1994 ; Lo_R.at(0, 7) = -0.0391; Lo_R.at(0, 8) = 0.0295 ; Lo_R.at(0, 9) = 0.0273; // 创建Hi_D Hi_R = cv::Mat(1, 10, CV_64FC1); Hi_R.at(0, 0) = 0.0273 ; Hi_R.at(0, 1) = -0.0295; Hi_R.at(0, 2) = -0.0391; Hi_R.at(0, 3) = -0.1994; Hi_R.at(0, 4) = 0.7234 ; Hi_R.at(0, 5) = -0.6340; Hi_R.at(0, 6) = 0.0166 ; Hi_R.at(0, 7) = 0.1753 ; Hi_R.at(0, 8) = -0.0211; Hi_R.at(0, 9) = -0.0195; } else if (wname == "sym6") { // 创建Lo_D Lo_R = cv::Mat(1, 12, CV_64FC1); Lo_R.at(0, 0) = -0.0078; Lo_R.at(0, 1) = 0.0018 ; Lo_R.at(0, 2) = 0.0447 ; Lo_R.at(0, 3) = -0.0211; Lo_R.at(0, 4) = -0.0726; Lo_R.at(0, 5) = 0.3379 ; Lo_R.at(0, 6) = 0.7876 ; Lo_R.at(0, 7) = 0.4911 ; Lo_R.at(0, 8) = -0.0483; Lo_R.at(0, 9) = -0.1180; Lo_R.at(0, 10) = 0.0035; Lo_R.at(0, 11) = 0.0154; // 创建Hi_D Hi_R = cv::Mat(1, 12, CV_64FC1); Hi_R.at(0, 0) = 0.0154; Hi_R.at(0, 1) = -0.0035; Hi_R.at(0, 2) = -0.1180; Hi_R.at(0, 3) = 0.0483 ; Hi_R.at(0, 4) = 0.4911 ; Hi_R.at(0, 5) = -0.7876; Hi_R.at(0, 6) = 0.3379 ; Hi_R.at(0, 7) = 0.0726 ; Hi_R.at(0, 8) = -0.0211; Hi_R.at(0, 9) = -0.0447; Hi_R.at(0, 10) = 0.0018; Hi_R.at(0, 11) = 0.0078; } else if (wname == "sym7") { // 创建Lo_D Lo_R = cv::Mat(1, 14, CV_64FC1); Lo_R.at(0, 0) = 0.0103 ; Lo_R.at(0, 1) = 0.0040 ; Lo_R.at(0, 2) = -0.1078; Lo_R.at(0, 3) = -0.1400; Lo_R.at(0, 4) = 0.2886 ; Lo_R.at(0, 5) = 0.7678 ; Lo_R.at(0, 6) = 0.5361 ; Lo_R.at(0, 7) = 0.0174 ; Lo_R.at(0, 8) = -0.0496; Lo_R.at(0, 9) = 0.0679; Lo_R.at(0, 10) = 0.0305 ; Lo_R.at(0, 11) = -0.0126; Lo_R.at(0, 12) = -0.0010; Lo_R.at(0, 13) = 0.0027; // 创建Hi_D Hi_R = cv::Mat(1, 14, CV_64FC1); Hi_R.at(0, 0) = 0.0027 ; Hi_R.at(0, 1) = 0.0010 ; Hi_R.at(0, 2) = -0.0126; Hi_R.at(0, 3) = -0.0305; Hi_R.at(0, 4) = 0.0679 ; Hi_R.at(0, 5) = 0.0496 ; Hi_R.at(0, 6) = 0.0174 ; Hi_R.at(0, 7) = -0.5361; Hi_R.at(0, 8) = 0.7678 ; Hi_R.at(0, 9) = -0.2886; Hi_R.at(0, 10) = -0.1400; Hi_R.at(0, 11) = 0.1078 ; Hi_R.at(0, 12) = 0.0040 ; Hi_R.at(0, 13) = -0.0103; } else if (wname == "sym8") { // 创建Lo_D Lo_R = cv::Mat(1, 16, CV_64FC1); Lo_R.at(0, 0) = 0.0019; Lo_R.at(0, 1) = -0.0003; Lo_R.at(0, 2) = -0.0150; Lo_R.at(0, 3) = 0.0038 ; Lo_R.at(0, 4) = 0.0491 ; Lo_R.at(0, 5) = -0.0272; Lo_R.at(0, 6) = -0.0519; Lo_R.at(0, 7) = 0.3644 ; Lo_R.at(0, 8) = 0.7772 ; Lo_R.at(0, 9) = 0.4814; Lo_R.at(0, 10) = -0.0613; Lo_R.at(0, 11) = -0.1433; Lo_R.at(0, 12) = 0.0076 ; Lo_R.at(0, 13) = 0.0317 ; Lo_R.at(0, 14) = -0.0005; Lo_R.at(0, 15) = -0.0034; // 创建Hi_D Hi_R = cv::Mat(1, 16, CV_64FC1); Hi_R.at(0, 0) = -0.0034; Hi_R.at(0, 1) = 0.0005 ; Hi_R.at(0, 2) = 0.0317 ; Hi_R.at(0, 3) = -0.0076; Hi_R.at(0, 4) = -0.1433; Hi_R.at(0, 5) = 0.0613 ; Hi_R.at(0, 6) = 0.4814 ; Hi_R.at(0, 7) = -0.7772; Hi_R.at(0, 8) = 0.3644 ; Hi_R.at(0, 9) = 0.0519; Hi_R.at(0, 10) = -0.0272; Hi_R.at(0, 11) = -0.0491; Hi_R.at(0, 12) = 0.0038 ; Hi_R.at(0, 13) = 0.0150 ; Hi_R.at(0, 14) = -0.0003; Hi_R.at(0, 15) = -0.0019; } else if (wname == "sym9") { // 创建Lo_D Lo_R = cv::Mat(1, 18, CV_64FC1); Lo_R.at(0, 0) = 0.0011 ; Lo_R.at(0, 1) = -0.0005; Lo_R.at(0, 2) = -0.0103; Lo_R.at(0, 3) = 0.0089 ; Lo_R.at(0, 4) = 0.0621 ; Lo_R.at(0, 5) = -0.0182; Lo_R.at(0, 6) = -0.1916; Lo_R.at(0, 7) = 0.0353 ; Lo_R.at(0, 8) = 0.6173 ; Lo_R.at(0, 9) = 0.7179; Lo_R.at(0, 10) = 0.2388 ; Lo_R.at(0, 11) = -0.0546; Lo_R.at(0, 12) = 0.0006 ; Lo_R.at(0, 13) = 0.0302 ; Lo_R.at(0, 14) = -0.0115; Lo_R.at(0, 15) = -0.0133; Lo_R.at(0, 16) = 0.0006 ; Lo_R.at(0, 17) = 0.0014; // 创建Hi_D Hi_R = cv::Mat(1, 18, CV_64FC1); Hi_R.at(0, 0) = 0.0014 ; Hi_R.at(0, 1) = -0.0006; Hi_R.at(0, 2) = -0.0133; Hi_R.at(0, 3) = 0.0115 ; Hi_R.at(0, 4) = 0.0302 ; Hi_R.at(0, 5) = -0.0006; Hi_R.at(0, 6) = -0.0546; Hi_R.at(0, 7) = -0.2388; Hi_R.at(0, 8) = 0.7179 ; Hi_R.at(0, 9) = -0.6173; Hi_R.at(0, 10) = 0.0353 ; Hi_R.at(0, 11) = 0.1916 ; Hi_R.at(0, 12) = -0.0182; Hi_R.at(0, 13) = -0.0621; Hi_R.at(0, 14) = 0.0089 ; Hi_R.at(0, 15) = 0.0103 ; Hi_R.at(0, 16) = -0.0005; Hi_R.at(0, 17) = -0.0011; } else if (wname == "sym10") { // 创建Lo_D Lo_R = cv::Mat(1, 20, CV_64FC1); Lo_R.at(0, 0) = -0.0005; Lo_R.at(0, 1) = 0.0001 ; Lo_R.at(0, 2) = 0.0046 ; Lo_R.at(0, 3) = -0.0008; Lo_R.at(0, 4) = -0.0204; Lo_R.at(0, 5) = 0.0058 ; Lo_R.at(0, 6) = 0.0500 ; Lo_R.at(0, 7) = -0.0320; Lo_R.at(0, 8) = -0.0355; Lo_R.at(0, 9) = 0.3838; Lo_R.at(0, 10) = 0.7695 ; Lo_R.at(0, 11) = 0.4717 ; Lo_R.at(0, 12) = -0.0709; Lo_R.at(0, 13) = -0.1595; Lo_R.at(0, 14) = 0.0116 ; Lo_R.at(0, 15) = 0.0459 ; Lo_R.at(0, 16) = -0.0015; Lo_R.at(0, 17) = -0.0086; Lo_R.at(0, 18) = 0.0001 ; Lo_R.at(0, 19) = 0.0008; // 创建Hi_D Hi_R = cv::Mat(1, 20, CV_64FC1); Hi_R.at(0, 0) = 0.0008 ; Hi_R.at(0, 1) = -0.0001; Hi_R.at(0, 2) = -0.0086; Hi_R.at(0, 3) = 0.0015 ; Hi_R.at(0, 4) = 0.0459 ; Hi_R.at(0, 5) = -0.0116; Hi_R.at(0, 6) = -0.1595; Hi_R.at(0, 7) = 0.0709 ; Hi_R.at(0, 8) = 0.4717 ; Hi_R.at(0, 9) = -0.7695; Hi_R.at(0, 10) = 0.3838 ; Hi_R.at(0, 11) = 0.0355 ; Hi_R.at(0, 12) = -0.0320; Hi_R.at(0, 13) = -0.0500; Hi_R.at(0, 14) = 0.0058 ; Hi_R.at(0, 15) = 0.0204 ; Hi_R.at(0, 16) = -0.0008; Hi_R.at(0, 17) = -0.0046; Hi_R.at(0, 18) = 0.0001 ; Hi_R.at(0, 19) = 0.0005; } else if (wname == "db1") { // 创建Lo_D Lo_R = cv::Mat(1, 2, CV_64FC1); Lo_R.at(0, 0) = 0.7071; Lo_R.at(0, 1) = 0.7071; // 创建Hi_D Hi_R = cv::Mat(1, 2, CV_64FC1); Hi_R.at(0, 0) = 0.7071; Hi_R.at(0, 1) = -0.7071; } else if (wname == "db2") { // 创建Lo_D Lo_R = cv::Mat(1, 4, CV_64FC1); Lo_R.at(0, 0) = 0.4830 ; Lo_R.at(0, 1) = 0.8365 ; Lo_R.at(0, 2) = 0.2241 ; Lo_R.at(0, 3) = -0.1294; // 创建Hi_D Hi_R = cv::Mat(1, 4, CV_64FC1); Hi_R.at(0, 0) = -0.1294; Hi_R.at(0, 1) = -0.2241; Hi_R.at(0, 2) = 0.8365 ; Hi_R.at(0, 3) = -0.4830; } else if (wname == "db3") { // 创建Lo_D Lo_R = cv::Mat(1, 6, CV_64FC1); Lo_R.at(0, 0) = 0.3327 ; Lo_R.at(0, 1) = 0.8069 ; Lo_R.at(0, 2) = 0.4599 ; Lo_R.at(0, 3) = -0.1350; Lo_R.at(0, 4) = -0.0854; Lo_R.at(0, 5) = 0.0352; // 创建Hi_D Hi_R = cv::Mat(1, 6, CV_64FC1) ; Hi_R.at(0, 0) = 0.0352 ; Hi_R.at(0, 1) = 0.0854 ; Hi_R.at(0, 2) = -0.1350; Hi_R.at(0, 3) = -0.4599; Hi_R.at(0, 4) = 0.8069 ; Hi_R.at(0, 5) = -0.3327; } else if (wname == "db4") { // 创建Lo_D Lo_R = cv::Mat(1, 8, CV_64FC1); Lo_R.at(0, 0) = 0.2304 ; Lo_R.at(0, 1) = 0.7148 ; Lo_R.at(0, 2) = 0.6309 ; Lo_R.at(0, 3) = -0.0280; Lo_R.at(0, 4) = -0.1870; Lo_R.at(0, 5) = 0.0308 ; Lo_R.at(0, 6) = 0.0329 ; Lo_R.at(0, 7) = -0.0106; // 创建Hi_D Hi_R = cv::Mat(1, 8, CV_64FC1); Hi_R.at(0, 0) = -0.0106; Hi_R.at(0, 1) = -0.0329; Hi_R.at(0, 2) = 0.0308 ; Hi_R.at(0, 3) = 0.1870 ; Hi_R.at(0, 4) = -0.0280; Hi_R.at(0, 5) = -0.6309; Hi_R.at(0, 6) = 0.7148 ; Hi_R.at(0, 7) = -0.2304; } else if (wname == "db5") { // 创建Lo_D Lo_R = cv::Mat(1, 10, CV_64FC1); Lo_R.at(0, 0) = 0.1601 ; Lo_R.at(0, 1) = 0.6038 ; Lo_R.at(0, 2) = 0.7243 ; Lo_R.at(0, 3) = 0.1384 ; Lo_R.at(0, 4) = -0.2423; Lo_R.at(0, 5) = -0.0322; Lo_R.at(0, 6) = 0.0776 ; Lo_R.at(0, 7) = -0.0062; Lo_R.at(0, 8) = -0.0126; Lo_R.at(0, 9) = 0.0033; // 创建Hi_D Hi_R = cv::Mat(1, 10, CV_64FC1); Hi_R.at(0, 0) = 0.0033 ; Hi_R.at(0, 1) = 0.0126 ; Hi_R.at(0, 2) = -0.0062; Hi_R.at(0, 3) = -0.0776; Hi_R.at(0, 4) = -0.0322; Hi_R.at(0, 5) = 0.2423 ; Hi_R.at(0, 6) = 0.1384 ; Hi_R.at(0, 7) = -0.7243; Hi_R.at(0, 8) = 0.6038 ; Hi_R.at(0, 9) = -0.1601; } else if (wname == "db6") { // 创建Lo_D Lo_R = cv::Mat(1, 12, CV_64FC1); Lo_R.at(0, 0) = 0.1115 ; Lo_R.at(0, 1) = 0.4946 ; Lo_R.at(0, 2) = 0.7511 ; Lo_R.at(0, 3) = 0.3153 ; Lo_R.at(0, 4) = -0.2263; Lo_R.at(0, 5) = -0.1298; Lo_R.at(0, 6) = 0.0975 ; Lo_R.at(0, 7) = 0.0275 ; Lo_R.at(0, 8) = -0.0316; Lo_R.at(0, 9) = 0.0006; Lo_R.at(0, 10) = 0.0048 ; Lo_R.at(0, 11) = -0.0011; // 创建Hi_D Hi_R = cv::Mat(1, 12, CV_64FC1); Hi_R.at(0, 0) = -0.0011; Hi_R.at(0, 1) = -0.0048; Hi_R.at(0, 2) = 0.0006 ; Hi_R.at(0, 3) = 0.0316 ; Hi_R.at(0, 4) = 0.0275 ; Hi_R.at(0, 5) = -0.0975; Hi_R.at(0, 6) = -0.1298; Hi_R.at(0, 7) = 0.2263 ; Hi_R.at(0, 8) = 0.3153 ; Hi_R.at(0, 9) = -0.7511; Hi_R.at(0, 10) = 0.4946 ; Hi_R.at(0, 11) = -0.1115; } else if (wname == "db7") { // 创建Lo_D Lo_R = cv::Mat(1, 14, CV_64FC1); Lo_R.at(0, 0) = 0.0779 ; Lo_R.at(0, 1) = 0.3965 ; Lo_R.at(0, 2) = 0.7291 ; Lo_R.at(0, 3) = 0.4698 ; Lo_R.at(0, 4) = -0.1439; Lo_R.at(0, 5) = -0.2240; Lo_R.at(0, 6) = 0.0713 ; Lo_R.at(0, 7) = 0.0806 ; Lo_R.at(0, 8) = -0.0380; Lo_R.at(0, 9) = -0.0166; Lo_R.at(0, 10) = 0.0126 ; Lo_R.at(0, 11) = 0.0004 ; Lo_R.at(0, 12) = -0.0018; Lo_R.at(0, 13) = 0.0004; // 创建Hi_D Hi_R = cv::Mat(1, 14, CV_64FC1); Hi_R.at(0, 0) = 0.0004 ; Hi_R.at(0, 1) = 0.0018 ; Hi_R.at(0, 2) = 0.0004 ; Hi_R.at(0, 3) = -0.0126; Hi_R.at(0, 4) = -0.0166; Hi_R.at(0, 5) = 0.0380 ; Hi_R.at(0, 6) = 0.0806 ; Hi_R.at(0, 7) = -0.0713; Hi_R.at(0, 8) = -0.2240; Hi_R.at(0, 9) = 0.1439; Hi_R.at(0, 10) = 0.4698 ; Hi_R.at(0, 11) = -0.7291; Hi_R.at(0, 12) = 0.3965 ; Hi_R.at(0, 13) = -0.0779; } else if (wname == "db8") { // 创建Lo_D Lo_R = cv::Mat(1, 16, CV_64FC1); Lo_R.at(0, 0) = 0.0544 ; Lo_R.at(0, 1) = 0.3129; Lo_R.at(0, 2) = 0.6756 ; Lo_R.at(0, 3) = 0.5854; Lo_R.at(0, 4) = -0.0158; Lo_R.at(0, 5) = -0.2840; Lo_R.at(0, 6) = 0.0005 ; Lo_R.at(0, 7) = 0.1287 ; Lo_R.at(0, 8) = -0.0174; Lo_R.at(0, 9) = -0.0441; Lo_R.at(0, 10) = 0.0140 ; Lo_R.at(0, 11) = 0.0087 ; Lo_R.at(0, 12) = -0.0049; Lo_R.at(0, 13) = -0.0004; Lo_R.at(0, 14) = 0.0007 ; Lo_R.at(0, 15) = -0.0001; // 创建Hi_D Hi_R = cv::Mat(1, 16, CV_64FC1); Hi_R.at(0, 0) = -0.0001; Hi_R.at(0, 1) = -0.0007; Hi_R.at(0, 2) = -0.0004; Hi_R.at(0, 3) = 0.0049 ; Hi_R.at(0, 4) = 0.0087 ; Hi_R.at(0, 5) = -0.0140; Hi_R.at(0, 6) = -0.0441; Hi_R.at(0, 7) = 0.0174 ; Hi_R.at(0, 8) = 0.1287 ; Hi_R.at(0, 9) = -0.0005; Hi_R.at(0, 10) = -0.2840; Hi_R.at(0, 11) = 0.0158 ; Hi_R.at(0, 12) = 0.5854 ; Hi_R.at(0, 13) = -0.6756; Hi_R.at(0, 14) = 0.3129 ; Hi_R.at(0, 15) = -0.0544; } else if (wname == "db9") { // 创建Lo_D Lo_R = cv::Mat(1, 18, CV_64FC1); Lo_R.at(0, 0) = 0.0381 ; Lo_R.at(0, 1) = 0.2438 ; Lo_R.at(0, 2) = 0.6048 ; Lo_R.at(0, 3) = 0.6573 ; Lo_R.at(0, 4) = 0.1332 ; Lo_R.at(0, 5) = -0.2933; Lo_R.at(0, 6) = -0.0968; Lo_R.at(0, 7) = 0.1485 ; Lo_R.at(0, 8) = 0.0307 ; Lo_R.at(0, 9) = -0.0676; Lo_R.at(0, 10) = 0.0003 ; Lo_R.at(0, 11) = 0.0224 ; Lo_R.at(0, 12) = -0.0047; Lo_R.at(0, 13) = -0.0043; Lo_R.at(0, 14) = 0.0018 ; Lo_R.at(0, 15) = 0.0002 ; Lo_R.at(0, 16) = -0.0003; Lo_R.at(0, 17) = 0.0000 ; // 创建Hi_D Hi_R = cv::Mat(1, 18, CV_64FC1); Hi_R.at(0, 0) = 0.0000 ; Hi_R.at(0, 1) = 0.0003 ; Hi_R.at(0, 2) = 0.0002 ; Hi_R.at(0, 3) = -0.0018; Hi_R.at(0, 4) = -0.0043; Hi_R.at(0, 5) = 0.0047 ; Hi_R.at(0, 6) = 0.0224 ; Hi_R.at(0, 7) = -0.0003; Hi_R.at(0, 8) = -0.0676; Hi_R.at(0, 9) = -0.0307; Hi_R.at(0, 10) = 0.1485 ; Hi_R.at(0, 11) = 0.0968 ; Hi_R.at(0, 12) = -0.2933; Hi_R.at(0, 13) = -0.1332; Hi_R.at(0, 14) = 0.6573 ; Hi_R.at(0, 15) = -0.6048; Hi_R.at(0, 16) = 0.2438 ; Hi_R.at(0, 17) = -0.0381; } else if (wname == "db10") { // 创建Lo_D Lo_R = cv::Mat(1, 20, CV_64FC1); Lo_R.at(0, 0) = 0.0267 ; Lo_R.at(0, 1) = 0.1882 ; Lo_R.at(0, 2) = 0.5272 ; Lo_R.at(0, 3) = 0.6885 ; Lo_R.at(0, 4) = 0.2812 ; Lo_R.at(0, 5) = -0.2498; Lo_R.at(0, 6) = -0.1959; Lo_R.at(0, 7) = 0.1274 ; Lo_R.at(0, 8) = 0.0931 ; Lo_R.at(0, 9) = -0.0714; Lo_R.at(0, 10) = -0.0295; Lo_R.at(0, 11) = 0.0332 ; Lo_R.at(0, 12) = 0.0036 ; Lo_R.at(0, 13) = -0.0107; Lo_R.at(0, 14) = 0.0014 ; Lo_R.at(0, 15) = 0.0020 ; Lo_R.at(0, 16) = -0.0007; Lo_R.at(0, 17) = -0.0001; Lo_R.at(0, 18) = 0.0001 ; Lo_R.at(0, 19) = -0.0000; // 创建Hi_D Hi_R = cv::Mat(1, 20, CV_64FC1); Hi_R.at(0, 0) = -0.0000; Hi_R.at(0, 1) = -0.0001; Hi_R.at(0, 2) = -0.0001; Hi_R.at(0, 3) = 0.0007 ; Hi_R.at(0, 4) = 0.0020 ; Hi_R.at(0, 5) = -0.0014; Hi_R.at(0, 6) = -0.0107; Hi_R.at(0, 7) = -0.0036; Hi_R.at(0, 8) = 0.0332 ; Hi_R.at(0, 9) = 0.0295; Hi_R.at(0, 10) = -0.0714; Hi_R.at(0, 11) = -0.0931; Hi_R.at(0, 12) = 0.1274 ; Hi_R.at(0, 13) = 0.1959 ; Hi_R.at(0, 14) = -0.2498; Hi_R.at(0, 15) = -0.2812; Hi_R.at(0, 16) = 0.6885 ; Hi_R.at(0, 17) = -0.5272; Hi_R.at(0, 18) = 0.1882 ; Hi_R.at(0, 19) = -0.0267; } // coiflet小波 else if (wname == "coif1") { // 创建Lo_R Lo_R = cv::Mat(1, 6, CV_64FC1); Lo_R.at(0, 0) = -0.0727; Lo_R.at(0, 1) = 0.3379 ; Lo_R.at(0, 2) = 0.8526 ; Lo_R.at(0, 3) = 0.3849 ; Lo_R.at(0, 4) = -0.0727; Lo_R.at(0, 5) = -0.0157; // 创建Hi_R Hi_R = cv::Mat(1, 6, CV_64FC1); Hi_R.at(0, 0) = -0.0157 ; Hi_R.at(0, 1) = 0.0727; Hi_R.at(0, 2) = 0.3849 ; Hi_R.at(0, 3) = -0.8526 ; Hi_R.at(0, 4) = 0.3379; Hi_R.at(0, 5) = 0.0727; } else if (wname == "coif2") { // 创建Lo_R Lo_R = cv::Mat(1, 12, CV_64FC1); Lo_R.at(0, 0) = 0.0164; Lo_R.at(0, 1) = -0.0415; Lo_R.at(0, 2) = -0.0674; Lo_R.at(0, 3) = 0.3861; Lo_R.at(0, 4) = 0.8127; Lo_R.at(0, 5) = 0.4170; Lo_R.at(0, 6) = -0.0765; Lo_R.at(0, 7) = -0.0594; Lo_R.at(0, 8) = 0.0237; Lo_R.at(0, 9) = 0.0056; Lo_R.at(0, 10) = -0.0018; Lo_R.at(0, 11) = -0.0007; // 创建Hi_R Hi_R = cv::Mat(1, 12, CV_64FC1); Hi_R.at(0, 0) = -0.0007; Hi_R.at(0, 1) = 0.0018 ; Hi_R.at(0, 2) = 0.0056 ; Hi_R.at(0, 3) = -0.0237; Hi_R.at(0, 4) = -0.0594; Hi_R.at(0, 5) = 0.0765 ; Hi_R.at(0, 6) = 0.4170 ; Hi_R.at(0, 7) = -0.8127; Hi_R.at(0, 8) = 0.3861 ; Hi_R.at(0, 9) = 0.0674 ; Hi_R.at(0, 10) = -0.0415; Hi_R.at(0, 11) = -0.0164; } else if (wname == "coif3") { // 创建Lo_R Lo_R = cv::Mat(1, 18, CV_64FC1); Lo_R.at(0, 0) = -0.0038; Lo_R.at(0, 1) = 0.0078 ; Lo_R.at(0, 2) = 0.0235 ; Lo_R.at(0, 3) = -0.0658; Lo_R.at(0, 4) = -0.0611; Lo_R.at(0, 5) = 0.4052 ; Lo_R.at(0, 6) = 0.7938 ; Lo_R.at(0, 7) = 0.4285 ; Lo_R.at(0, 8) = -0.0718; Lo_R.at(0, 9) = -0.0823; Lo_R.at(0, 10) = 0.0346 ; Lo_R.at(0, 11) = 0.0159 ; Lo_R.at(0, 12) = -0.0090; Lo_R.at(0, 13) = -0.0026; Lo_R.at(0, 14) = 0.0011 ; Lo_R.at(0, 15) = 0.0005 ; Lo_R.at(0, 16) = -0.0001; Lo_R.at(0, 17) = -0.0000; // 创建Hi_R Hi_R = cv::Mat(1, 18, CV_64FC1); Hi_R.at(0, 0) = -0.0000; Hi_R.at(0, 1) = 0.0001 ; Hi_R.at(0, 2) = 0.0005 ; Hi_R.at(0, 3) = -0.0011; Hi_R.at(0, 4) = -0.0026; Hi_R.at(0, 5) = 0.0090 ; Hi_R.at(0, 6) = 0.0159 ; Hi_R.at(0, 7) = -0.0346; Hi_R.at(0, 8) = -0.0823; Hi_R.at(0, 9) = 0.0718; Hi_R.at(0, 10) = 0.4285 ; Hi_R.at(0, 11) = -0.7938; Hi_R.at(0, 12) = 0.4052 ; Hi_R.at(0, 13) = 0.0611 ; Hi_R.at(0, 14) = -0.0658; Hi_R.at(0, 15) = -0.0235; Hi_R.at(0, 16) = 0.0078 ; Hi_R.at(0, 17) = 0.0038; } else if (wname == "coif4") { // 创建Lo_R Lo_R = cv::Mat(1, 24, CV_64FC1); Lo_R.at(0, 0) = 0.0009 ; Lo_R.at(0, 1) = -0.0016; Lo_R.at(0, 2) = -0.0073; Lo_R.at(0, 3) = 0.0161 ; Lo_R.at(0, 4) = 0.0267 ; Lo_R.at(0, 5) = -0.0813; Lo_R.at(0, 6) = -0.0561; Lo_R.at(0, 7) = 0.4153 ; Lo_R.at(0, 8) = 0.7822 ; Lo_R.at(0, 9) = 0.4344; Lo_R.at(0, 10) = -0.0666; Lo_R.at(0, 11) = -0.0962; Lo_R.at(0, 12) = 0.0393 ; Lo_R.at(0, 13) = 0.0251 ; Lo_R.at(0, 14) = -0.0152; Lo_R.at(0, 15) = -0.0057; Lo_R.at(0, 16) = 0.0038 ; Lo_R.at(0, 17) = 0.0013 ; Lo_R.at(0, 18) = -0.0006; Lo_R.at(0, 19) = -0.0003; Lo_R.at(0, 20) = 0.0001 ; Lo_R.at(0, 21) = 0.0000 ; Lo_R.at(0, 22) = -0.0000; Lo_R.at(0, 23) = -0.0000; // 创建Hi_R Hi_R = cv::Mat(1, 24, CV_64FC1); Hi_R.at(0, 0) = -0.0000; Hi_R.at(0, 1) = 0.0000 ; Hi_R.at(0, 2) = 0.0000 ; Hi_R.at(0, 3) = -0.0001; Hi_R.at(0, 4) = -0.0003; Hi_R.at(0, 5) = 0.0006 ; Hi_R.at(0, 6) = 0.0013 ; Hi_R.at(0, 7) = -0.0038; Hi_R.at(0, 8) = -0.0057; Hi_R.at(0, 9) = 0.0152 ; Hi_R.at(0, 10) = 0.0251 ; Hi_R.at(0, 11) = -0.0393; Hi_R.at(0, 12) = -0.0962; Hi_R.at(0, 13) = 0.0666 ; Hi_R.at(0, 14) = 0.4344 ; Hi_R.at(0, 15) = -0.7822; Hi_R.at(0, 16) = 0.4153 ; Hi_R.at(0, 17) = 0.0561 ; Hi_R.at(0, 18) = -0.0813; Hi_R.at(0, 19) = -0.0267; Hi_R.at(0, 20) = 0.0161 ; Hi_R.at(0, 21) = 0.0073 ; Hi_R.at(0, 22) = -0.0016; Hi_R.at(0, 23) = -0.0009; } else if (wname == "coif5") { // 创建Lo_R Lo_R = cv::Mat(1, 30, CV_64FC1); Lo_R.at(0, 0) = -0.0002; Lo_R.at(0, 1) = 0.0004 ; Lo_R.at(0, 2) = 0.0022 ; Lo_R.at(0, 3) = -0.0042; Lo_R.at(0, 4) = -0.0101; Lo_R.at(0, 5) = 0.0234 ; Lo_R.at(0, 6) = 0.0282 ; Lo_R.at(0, 7) = -0.0919; Lo_R.at(0, 8) = -0.0520; Lo_R.at(0, 9) = 0.4216; Lo_R.at(0, 10) = 0.7743 ; Lo_R.at(0, 11) = 0.4380 ; Lo_R.at(0, 12) = -0.0620; Lo_R.at(0, 13) = -0.1056; Lo_R.at(0, 14) = 0.0413 ; Lo_R.at(0, 15) = 0.0327 ; Lo_R.at(0, 16) = -0.0198; Lo_R.at(0, 17) = -0.0092; Lo_R.at(0, 18) = 0.0068 ; Lo_R.at(0, 19) = 0.0024 ; Lo_R.at(0, 20) = -0.0017; Lo_R.at(0, 21) = -0.0006; Lo_R.at(0, 22) = 0.0003 ; Lo_R.at(0, 23) = 0.0001 ; Lo_R.at(0, 24) = -0.0000 ; Lo_R.at(0, 25) = -0.0000; Lo_R.at(0, 26) = 0.0000 ; Lo_R.at(0, 27) = 0.0000 ; Lo_R.at(0, 28) = -0.0000; Lo_R.at(0, 29) = -0.0000; // 创建Hi_R Hi_R = cv::Mat(1, 30, CV_64FC1); Hi_R.at(0, 0) = -0.0000; Hi_R.at(0, 1) = 0.0000 ; Hi_R.at(0, 2) = 0.0000 ; Hi_R.at(0, 3) = -0.0000; Hi_R.at(0, 4) = -0.0000; Hi_R.at(0, 5) = 0.0000 ; Hi_R.at(0, 6) = 0.0001 ; Hi_R.at(0, 7) = -0.0003; Hi_R.at(0, 8) = -0.0006; Hi_R.at(0, 9) = 0.0017; Hi_R.at(0, 10) = 0.0024 ; Hi_R.at(0, 11) = -0.0068; Hi_R.at(0, 12) = -0.0092; Hi_R.at(0, 13) = 0.0198 ; Hi_R.at(0, 14) = 0.0327 ; Hi_R.at(0, 15) = -0.0413; Hi_R.at(0, 16) = -0.1056; Hi_R.at(0, 17) = 0.0620 ; Hi_R.at(0, 18) = 0.4380 ; Hi_R.at(0, 19) = -0.7743; Hi_R.at(0, 20) = 0.4216 ; Hi_R.at(0, 21) = 0.0520 ; Hi_R.at(0, 22) = -0.0919; Hi_R.at(0, 23) = -0.0282; Hi_R.at(0, 24) = 0.0234 ; Hi_R.at(0, 25) = 0.0101 ; Hi_R.at(0, 26) = -0.0042; Hi_R.at(0, 27) = -0.0022; Hi_R.at(0, 28) = 0.0004 ; Hi_R.at(0, 29) = 0.0002; } else { return false; } return true; } // 功能:函数 waveRec2() 对输入的分解系数矩阵coef进行 level 层重构, 得到重构矩阵rec bool waveRec2(cv::Mat& rec, const std::deque &coef, const std::deque &scf, const string wname, const unsigned int level) { // 输入有效性判断 if ( level < 1 ) // 图像分解层数 level >= 1 { return false; } // 系数矩阵coef尺寸验证 if (coef.size() != 3 * level + 1) { return false; } // 系数矩阵coef:空值 + 数据类型验证 for (unsigned int i = 0; i < coef.size(); i++) { if (coef[i].empty() == true || (coef[i].type() != CV_64FC1)) { return false; } } // scf尺寸验证 if (scf.size() != level + 2) { return false; } // 数据正值判断 for (unsigned int i = 0; i < scf.size(); i++) { if (scf[i][0] <= 0 || scf[i][1] <= 0) { return false; } } // 求出小波函数对应的重构滤波器组系数向量 cv::Mat Lo_R; // 低频滤波器 cv::Mat Hi_R; // 高频滤波器 if (!getWaveRecFilter(Lo_R, Hi_R, wname)) { return false; } // Lo_R 、Lo_R创建有效性验证 if (Lo_R.empty() == true || Lo_R.empty() == true || Lo_R.size != Hi_R.size) { return false; } cv::Mat tmp_rec; // 临时结果 // 重构分量 cv::Mat rcA; cv::Mat rcV; cv::Mat rcH; cv::Mat rcD; // 获取低频分量 coef[0].copyTo(rcA); for (unsigned int i = 0; i < level; i++) { coef[i * 3 + 1].copyTo(rcV); coef[i * 3 + 2].copyTo(rcH); coef[i * 3 + 3].copyTo(rcD); // 二维小波逆变换 bool ret = idwt2(tmp_rec, rcA, rcV, rcH, rcD, Lo_R, Hi_R, scf[i + 2]); // 第i重构得到第i-1级低频 // 二维小波逆变换结果 if (ret == false) { return false; } else { tmp_rec.copyTo(rcA); // 更新低频分量 } } // 得到最终结果 tmp_rec.copyTo(rec); return true; }