实践高斯模糊卷积核生成公式(二维正态分布)

公式

维基百科中有如下记载:

高斯模糊是一种图像模糊滤波器,它用 正态分布计算图像中每个像素的变换。N维空间正态分布方程为:
G ( r ) = 1 2 π σ 2 N e − r 2 / ( 2 σ 2 ) G(r) = \frac{1}{\sqrt{2\pi \sigma^2}^N} e^{-r^2/(2 \sigma^2)}G (r )=2 πσ2 ​N 1 ​e −r 2 /(2 σ2 )

在二维空间定义为:
G ( u , v ) = 1 2 π σ 2 e − ( u 2 + v 2 ) / ( 2 σ 2 ) G(u,v) = \frac{1}{2\pi \sigma^2} e^{-(u^2 + v^2)/(2 \sigma^2)}G (u ,v )=2 πσ2 1 ​e −(u 2 +v 2 )/(2 σ2 )

其中:

  • r r r 是模糊半径,r 2 = u 2 + v 2 r^2 = u^2 + v^2 r 2 =u 2 +v 2
  • σ \sigma σ 是正态分布的 标准偏差

C++代码实现

将二维的公式翻译为C++代码如下:

double NormalDistribution(double u, double v, double sigma)
{
    const double r2 = u * u + v * v;
    const double exponent = -r2 / (2 * sigma*sigma);
    const double denominator = 2 * M_PI * sigma*sigma;
    return pow(M_E, exponent) / denominator;
}

为了验证其效果,尝试使用其生成一些卷积核。
生成的过程还包括计算 u u u、v v v(假定其分布在1.0的范围内),与归一化。
完整代码如下:

#include
#include
using namespace std;

#define M_PI 3.14159265358979323846
#define M_E  2.71828182845904523536

double NormalDistribution(double u, double v, double sigma)
{
    const double r2 = u * u + v * v;
    const double exponent = -r2 / (2 * sigma*sigma);
    const double denominator = 2 * M_PI * sigma*sigma;
    return pow(M_E, exponent) / denominator;
}

int main()
{

    const int KernelSize = 7;
    const double sigma = 0.15;

    double* Kernel = new double[KernelSize*KernelSize];

    const double step = 1.0 / KernelSize;

    double amount = 0;

    for (int y = 0; y < KernelSize; y++)
        for (int x = 0; x < KernelSize; x++)
        {
            double u = -0.5 + (0.5 + x)*(step);
            double v = -0.5 + (0.5 + y)*(step);
            double value = NormalDistribution(u, v, sigma);
            Kernel[y*KernelSize + x] = value;
            amount += value;
        }

    for (int i = 0; i < KernelSize*KernelSize; i++)
        Kernel[i] /= amount;

    for (int y = 0; y < KernelSize; y++)
    {
        for (int x = 0; x < KernelSize; x++)
        {
            cout << left<< setw(12)<< Kernel[y*KernelSize + x];
        }
        cout << endl;
    }
}

当 卷积核尺寸=3,标准偏差=0.3 时,结果如下:

0.067329    0.12482     0.067329
0.12482     0.231403    0.12482
0.067329    0.12482     0.067329

当 卷积核尺寸=7,标准偏差=0.15 时,结果如下:

4.1177e-05  0.000397602 0.00154998  0.00243941  0.00154998  0.000397602 4.1177e-05
0.000397602 0.00383923  0.0149665   0.0235548   0.0149665   0.00383923  0.000397602
0.00154998  0.0149665   0.0583442   0.0918241   0.0583442   0.0149665   0.00154998
0.00243941  0.0235548   0.0918241   0.144516    0.0918241   0.0235548   0.00243941
0.00154998  0.0149665   0.0583442   0.0918241   0.0583442   0.0149665   0.00154998
0.000397602 0.00383923  0.0149665   0.0235548   0.0149665   0.00383923  0.000397602
4.1177e-05  0.000397602 0.00154998  0.00243941  0.00154998  0.000397602 4.1177e-05

可以看到中心的值是最高的,随后越靠近边缘值越低,且变化不是线性的。

在着色器中计算,并预览标准偏差的影响

为了可以实时预览标准偏差的影响。我将公式翻译为了HLSL代码:

float r2 = u * u + v * v;
float exponent = -r2 / (2 * sigma*sigma);
float denominator = 2 * 3.1415926 * sigma*sigma;
return pow(2.7182818, exponent) / denominator;

然后将其放入UE的材质中借此预览:

实践高斯模糊卷积核生成公式(二维正态分布)
可以看到,标准偏差的值越小,就越集中:
实践高斯模糊卷积核生成公式(二维正态分布)

Original: https://blog.csdn.net/u013412391/article/details/122075117
Author: YakSue
Title: 实践高斯模糊卷积核生成公式(二维正态分布)

原创文章受到原创版权保护。转载请注明出处:https://www.johngo689.com/644717/

转载文章受原作者版权保护。转载请注明原作者出处!

(0)

大家都在看

亲爱的 Coder【最近整理,可免费获取】👉 最新必读书单  | 👏 面试题下载  | 🌎 免费的AI知识星球