Small speedup for denoise (mainly for preview mode), #5225

This commit is contained in:
heckflosse
2019-03-17 19:45:46 +01:00
parent 25625c6842
commit 9ee47c29a3
2 changed files with 20 additions and 72 deletions

View File

@@ -2112,52 +2112,7 @@ void ImProcFunctions::RGBoutput_tile_row(float *bloxrow_L, float ** Ldetail, flo
#undef epsilon
*/
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
//%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
float ImProcFunctions::MadMax(float * DataList, int & max, int datalen)
{
//computes Median Absolute Deviation and Maximum of DataList
//DataList values should mostly have abs val < 65535
int * histo = new int[65536];
//memset(histo, 0, 65536*sizeof(histo));
for (int i = 0; i < 65536; ++i) {
histo[i] = 0;
}
//calculate histogram of absolute values of HH wavelet coeffs
for (int i = 0; i < datalen; ++i) {
histo[MAX(0, MIN(65535, abs((int)DataList[i])))]++;
}
//find median of histogram
int median = 0, count = 0;
while (count < datalen / 2) {
count += histo[median];
++median;
}
//find max of histogram
max = 65535;
while (histo[max] == 0) {
max--;
}
int count_ = count - histo[median - 1];
delete[] histo;
// interpolate
return (((median - 1) + (datalen / 2 - count_) / (static_cast<float>(count - count_))) / 0.6745);
}
float ImProcFunctions::Mad(float * DataList, const int datalen)
float ImProcFunctions::Mad(const float * DataList, const int datalen)
{
if (datalen <= 1) { // Avoid possible buffer underrun
return 0;
@@ -2169,7 +2124,7 @@ float ImProcFunctions::Mad(float * DataList, const int datalen)
//calculate histogram of absolute values of wavelet coeffs
for (int i = 0; i < datalen; ++i) {
histo[min(255, abs(static_cast<int>(DataList[i])))]++;
histo[static_cast<int>(rtengine::min(255.f, fabsf(DataList[i])))]++;
}
//find median of histogram
@@ -2186,7 +2141,7 @@ float ImProcFunctions::Mad(float * DataList, const int datalen)
return (((median - 1) + (datalen / 2 - count_) / (static_cast<float>(count - count_))) / 0.6745);
}
float ImProcFunctions::MadRgb(float * DataList, const int datalen)
float ImProcFunctions::MadRgb(const float * DataList, const int datalen)
{
if (datalen <= 1) { // Avoid possible buffer underrun
return 0;
@@ -2201,10 +2156,8 @@ float ImProcFunctions::MadRgb(float * DataList, const int datalen)
}
//calculate histogram of absolute values of wavelet coeffs
int i;
for (i = 0; i < datalen; ++i) {
histo[min(65535, abs(static_cast<int>(DataList[i])))]++;
for (int i = 0; i < datalen; ++i) {
histo[static_cast<int>(rtengine::min(65535.f, fabsf(DataList[i])))]++;
}
//find median of histogram
@@ -2224,27 +2177,23 @@ float ImProcFunctions::MadRgb(float * DataList, const int datalen)
void ImProcFunctions::Noise_residualAB(wavelet_decomposition &WaveletCoeffs_ab, float &chresid, float &chmaxresid, bool denoiseMethodRgb)
void ImProcFunctions::Noise_residualAB(const wavelet_decomposition &WaveletCoeffs_ab, float &chresid, float &chmaxresid, bool denoiseMethodRgb)
{
int maxlvl = WaveletCoeffs_ab.maxlevel();
float resid = 0.f;
float madC;
float maxresid = 0.f;
for (int lvl = 0; lvl < maxlvl; ++lvl) {
#ifdef _OPENMP
#pragma omp parallel for schedule(dynamic) collapse(2) reduction(+:resid) reduction(max:maxresid) num_threads(denoiseNestedLevels) if (denoiseNestedLevels>1)
#endif
for (int lvl = 0; lvl < WaveletCoeffs_ab.maxlevel(); ++lvl) {
// compute median absolute deviation (MAD) of detail coefficients as robust noise estimator
int Wlvl_ab = WaveletCoeffs_ab.level_W(lvl);
int Hlvl_ab = WaveletCoeffs_ab.level_H(lvl);
float ** WavCoeffs_ab = WaveletCoeffs_ab.level_coeffs(lvl);
for (int dir = 1; dir < 4; ++dir) {
if (denoiseMethodRgb) {
madC = SQR(MadRgb(WavCoeffs_ab[dir], Wlvl_ab * Hlvl_ab));
} else {
madC = SQR(Mad(WavCoeffs_ab[dir], Wlvl_ab * Hlvl_ab));
}
const int Wlvl_ab = WaveletCoeffs_ab.level_W(lvl);
const int Hlvl_ab = WaveletCoeffs_ab.level_H(lvl);
float ** WavCoeffs_ab = WaveletCoeffs_ab.level_coeffs(lvl);
const float madC = SQR(denoiseMethodRgb ? MadRgb(WavCoeffs_ab[dir], Wlvl_ab * Hlvl_ab) : Mad(WavCoeffs_ab[dir], Wlvl_ab * Hlvl_ab));
resid += madC;
@@ -2624,7 +2573,7 @@ bool ImProcFunctions::WaveletDenoiseAllAB(wavelet_decomposition &WaveletCoeffs_L
if (!memoryAllocationFailed) {
#ifdef _OPENMP
#pragma omp for schedule(dynamic) collapse(2)
#pragma omp for schedule(dynamic) collapse(2) nowait
#endif
for (int lvl = 0; lvl < maxlvl; ++lvl) {

View File

@@ -326,11 +326,10 @@ public:
void ShrinkAll_info(float ** WavCoeffs_a, float ** WavCoeffs_b,
int W_ab, int H_ab, float **noisevarlum, float **noisevarchrom, float **noisevarhue, float &chaut, int &Nb, float &redaut, float &blueaut, float &maxredaut, float &maxblueaut, float &minredaut, float &minblueaut, int schoice, int lvl, float &chromina, float &sigma, float &lumema, float &sigma_L, float &redyel, float &skinc, float &nsknc,
float &maxchred, float &maxchblue, float &minchred, float &minchblue, int &nb, float &chau, float &chred, float &chblue, bool denoiseMethodRgb);
void Noise_residualAB(wavelet_decomposition &WaveletCoeffs_ab, float &chresid, float &chmaxresid, bool denoiseMethodRgb);
void Noise_residualAB(const wavelet_decomposition &WaveletCoeffs_ab, float &chresid, float &chmaxresid, bool denoiseMethodRgb);
void calcautodn_info(float &chaut, float &delta, int Nb, int levaut, float maxmax, float lumema, float chromina, int mode, int lissage, float redyel, float skinc, float nsknc);
float MadMax(float * DataList, int &max, int datalen);
float Mad(float * DataList, const int datalen);
float MadRgb(float * DataList, const int datalen);
float Mad(const float * DataList, const int datalen);
float MadRgb(const float * DataList, const int datalen);
// pyramid wavelet
void dirpyr_equalizer(float ** src, float ** dst, int srcwidth, int srcheight, float ** l_a, float ** l_b, const double * mult, const double dirpyrThreshold, const double skinprot, float b_l, float t_l, float t_r, int scale); //Emil's directional pyramid wavelet