我已将此Matlab各向异性扩散代码转换为C ++,但我没有得到所需的输出。我得到的只是一个黑色的图像。有人可以检查我的代码并提出任何建议吗?以下是我的代码:
const double lambda = 1 / 7;
const double k = 30;
const int iter = 1;
int ahN[3][3] = { {0, 1, 0}, {0, -1, 0}, {0, 0, 0} };
int ahS[3][3] = { {0, 0, 0}, {0, -1, 0}, {0, 1, 0} };
int ahE[3][3] = { {0, 0, 0}, {0, -1, 1}, {0, 0, 0} };
int ahW[3][3] = { {0, 0, 0}, {1, -1, 0}, {0, 0, 0} };
int ahNE[3][3] = { {0, 0, 1}, {0, -1, 0}, {0, 0, 0} };
int ahSE[3][3] = { {0, 0, 0}, {0, -1, 0}, {0, 0, 1} };
int ahSW[3][3] = { {0, 0, 0}, {0, -1, 0}, {1, 0, 0} };
int ahNW[3][3] = { {1, 0, 0}, {0, -1, 0}, {0, 0, 0} };
Mat hN = Mat(3, 3, CV_32FC1, &ahN);
Mat hS = Mat(3, 3, CV_32FC1, &ahS);
Mat hE = Mat(3, 3, CV_32FC1, &ahE);
Mat hW = Mat(3, 3, CV_32FC1, &ahW);
Mat hNE = Mat(3, 3, CV_32FC1, &ahNE);
Mat hSE = Mat(3, 3, CV_32FC1, &ahSE);
Mat hSW = Mat(3, 3, CV_32FC1, &ahSW);
Mat hNW = Mat(3, 3, CV_32FC1, &ahNW);
void anisotropicDiffusion(Mat &output, int width, int height) {
//mat initialisation
Mat nablaN, nablaS, nablaW, nablaE, nablaNE, nablaSE, nablaSW, nablaNW;
Mat cN, cS, cW, cE, cNE, cSE, cSW, cNW;
//depth of filters
int ddepth = -1;
//center pixel distance
double dx = 1, dy = 1, dd = sqrt(2);
double idxSqr = 1.0 / (dx * dx), idySqr = 1.0 / (dy * dy), iddSqr = 1 / (dd * dd);
for (int i = 0; i < iter; i++) {
//filters
filter2D(output, nablaN, ddepth, hN);
filter2D(output, nablaS, ddepth, hS);
filter2D(output, nablaW, ddepth, hW);
filter2D(output, nablaE, ddepth, hE);
filter2D(output, nablaNE, ddepth, hNE);
filter2D(output, nablaSE, ddepth, hSE);
filter2D(output, nablaSW, ddepth, hSW);
filter2D(output, nablaNW, ddepth, hNW);
//exponential flux
cN = nablaN / k;
cN.mul(cN);
cN = 1.0 / (1.0 + cN);
//exp(-cN, cN);
cS = nablaS / k;
cS.mul(cS);
cS = 1.0 / (1.0 + cS);
//exp(-cS, cS);
cW = nablaW / k;
cW.mul(cW);
cW = 1.0 / (1.0 + cW);
//exp(-cW, cW);
cE = nablaE / k;
cE.mul(cE);
cE = 1.0 / (1.0 + cE);
//exp(-cE, cE);
cNE = nablaNE / k;
cNE.mul(cNE);
cNE = 1.0 / (1.0 + cNE);
//exp(-cNE, cNE);
cSE = nablaSE / k;
cSE.mul(cSE);
cSE = 1.0 / (1.0 + cSE);
//exp(-cSE, cSE);
cSW = nablaSW / k;
cSW.mul(cSW);
cSW = 1.0 / (1.0 + cSW);
//exp(-cSW, cSW);
cNW = nablaNW / k;
cNW.mul(cNW);
cNW = 1.0 / (1.0 + cNW);
//exp(-cNW, cNW);
output = output + lambda * (idySqr * cN.mul(nablaN) + idySqr * cS.mul(nablaS) +
idxSqr * cW.mul(nablaW) + idxSqr * cE.mul(nablaE) +
iddSqr * cNE.mul(nablaNE) + iddSqr * cSE.mul(nablaSE) +
iddSqr * cNW.mul(nablaNW) + iddSqr * cSW.mul(nablaSW));
}
}
答案 0 :(得分:1)
看起来你需要分配乘法结果:
Mat C = A.mul(B);
和
int ahN[3][3] ....
应该是
float ahN[3][3] ....
答案 1 :(得分:0)
在c#中解决。易于翻译成c ++ 你需要这个变量:
IMAGE [height,width] =存储图像的整数数组
height =以像素为单位的图像高度
width =以像素为单位的图像宽度
/// <summary>Perona & Malik anisotropic difusion filter. (squared formula)</summary>
/// <param name="data">Image data</param>
/// <param name="dt">Heat difusion value. Upper = more rapid convergence.</param>
/// <param name="lambda">The shape of the diffusion coefficient g(), controlling the Perona Malik diffusion g(delta) = 1/((1 + delta2) / lambda2). Upper = more blurred image & more noise removed</param>
/// <param name="interations">Determines the maximum number of iteration steps of the filter. Upper = less speed & more noise removed</param>
private void PeronaMalik(int[,] image, double dt, int lambda, int interations)
{
try
{
//test parameters
if (dt < 0)
throw new Exception("DT negative value not allowed");
if (lambda < 0)
throw new Exception("lambda must be upper of 0");
if (interations <= 0)
throw new Exception("Iterations must be upper of 0");
//Make temp image
int[,] temp = new int[height, width];
Array.Copy(image, temp, image.Length);
//Precalculate tables (for speed up)
double[] precal = new double[512];
double lambda2 = lambda * lambda;
for (int f = 0; f < 512; f++)
{
int diff = f - 255;
precal[f] = -dt * diff * lambda2 / (lambda2 + diff * diff);
}
//Apply the filter
for (int n = 0; n < interations; n++)
{
for (int h = 0; h < height; h++)
for (int w = 0; w < width; w++)
{
int current = temp[h, w];
int px = w - 1;
int nx = w + 1;
int py = h - 1;
int ny = h + 1;
if (px < 0)
px = 0;
if (nx >= width)
nx = width - 1;
if (py < 0)
py = 0;
if (ny >= height)
ny = height - 1;
image[h, w] = (int)(precal[255 + current - temp[h, px]] +
precal[255 + current - temp[h, nx]] +
precal[255 + current - temp[py, w]] +
precal[255 + current - temp[ny, w]]) +
temp[h, w];
}
}
}
catch (Exception ex) { throw new Exception(ex.Message + "\r\nIn PeronaMalik"); }
}
解决方案是等式2.如果你想要方程1(指数),你可以改变预先表格中的ecuation:
precal[f] = -dt * delta * Math.Exp(-(delta * delta / lambda2));