之前在进行openCV的白平衡处理时看到一位大佬的文章
原文链接
这篇文章提出了在Java中实现openCV白平衡的处理问题一种行之有效的方法,给我带来了许多启发,但是这篇文章中的代码的执行速率一直不高,究其原因,是由于在下面这个函数中
public Mat changeRGB(Mat mat, double k) {
Mat newMat = new Mat(mat.size(), CvType.CV_8UC1);
for (int i = 0; i < mat.rows(); i++) {
for (int j = 0; j < mat.cols(); j++) {
double[] color = mat.get(i, j);
color[0] *= k;
newMat.put(i, j, color);
}
}
return newMat;
}
由于需要不断地循环,因此造成了非常大的延迟,为此,如果能有一种简洁的方法来代替函数中不断地循环过程,或许能够给代码的执行速率带来提升。
在查阅了相关资料之后,我找到了convertScaleAbs()
这个函数,该函数的构造如下:
public static void convertScaleAbs(Mat src, Mat dst, double alpha)
{
convertScaleAbs_1(src.nativeObj, dst.nativeObj, alpha);
return;
}
函数的三个参数分别为输入数组,输出数组以及乘数因子。
测试后的图像和上文连接中的代码显现了相同的效果,但是效率得到了很大的提升。
关键代码如下
//RGB三通道分离
List<Mat> splitMat = new ArrayList<Mat>();
Core.split(src, splitMat);
//得到RGB三个通道的均值
double meanB = Core.mean(splitMat.get(0)).val[0];
double meanG = Core.mean(splitMat.get(1)).val[0];
double meanR = Core.mean(splitMat.get(2)).val[0];
//调整RGB三个通道的增益
double kB = (meanB + meanG + meanR) / (3 * meanB);
double kG = (meanB + meanG + meanR) / (3 * meanG);
double kR = (meanB + meanG + meanR) / (3 * meanR);
//调整RGB三个通道的值
List<Mat> mergeMatList = new ArrayList<Mat>();
Mat merge = new Mat();
Mat newMat = new Mat(splitMat.get(0).size(), CvType.CV_8UC1);
Mat newMat1 = new Mat(splitMat.get(1).size(), CvType.CV_8UC1);
Mat newMat2 = new Mat(splitMat.get(2).size(), CvType.CV_8UC1);
convertScaleAbs(splitMat.get(0),newMat,kB);
convertScaleAbs(splitMat.get(1),newMat1,kG);
convertScaleAbs(splitMat.get(2),newMat2,kR);
mergeMatList.add(newMat);
mergeMatList.add(newMat1);
mergeMatList.add(newMat2);
//合并三通道
Core.merge(mergeMatList, merge);