4月はずっと、最近流行の AviUtl プラグインのNL-Means filter に触発されてノイズ除去のアルゴリズムである Non Local Means をいじくってた。
NL-Means は広域で平均を取って絵をべた塗りに近づけるため、AviUtl 界ではアニメによく効くと言われている様子。
これは畳み込みの一種であり、例えばよく使われている移動平均なんかは次のような感じで畳み込み
![]() |
![]() |
|
ガウスぼかしは次のようなので畳み込む。
![]() |
|
Non Local Means は畳み込む画素の周囲でマッチングを行って、その一致率でウエイトを作る。似通った領域では広く平均が取られ、似通っていない領域では平均されない。
一致率の出し方が工夫のしどころではあるけど、NL-Means filter では差の二乗和を d、係数を h とすると
exp(-d*h)
というように指数に入れている。差が無ければウエイトが 1 になり、差が少しでも大きくなるとすぐ 0 に落ち込む。
また、h が 0 であれば移動平均になり、h が大きくなるにつれ似通った領域のみ使われるようになる。最終的に h が無限大になれば元の画像に一致する。
![]() h が小さい場合 |
![]() h が大きい場合 |
| 0.1 | 0.2 | 0.5 |
| 0.8 | 1.0 | 0.1 |
| 0.2 | 0.6 | 0.4 |
この手法の特徴は、パターンが一致している部分のみを使うので、エッジが完全に保存される。メディアンフィルタでは落ちてしまうような一本の線でさえも保存される。
しかし、逆に一点のノイズであっても保存されてしまうので、結局強いノイズは予め他の手法で取り除いておかないといけない。
![]() メディアンフィルタ 移動平均に比べてエッジが保存されている |
Non Local Means のみで強いノイズを除去するには h の値を小さくしないといけないが、それだと移動平均に近づくのでボケる。
h を小さくしつつボケにくくする為には、畳み込みのサイズを小さくするしか無い。それでは広く平均を取れるこの手法の利点が薄くなる。
そこで折衷案として、h を 0 にした時にガウスぼかしになるようにしてみた。
こうすると領域は円形になるし、サイズを小数単位で微調整出来る。何より遠くにいく程弱くなるので、広過ぎる範囲で平均されない。
![]() ガウスぼかしに近づく方法で h を小さくした場合 |
うーん。SAMSUNG の文字は多少読みやすくなってるけど、あまり差が無いかな。






