1
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

pix2pixでCFAデモザイクを試してみる

Posted at

pix2pixでCFAデモザイクを試してみる

はじめに

画像から画像を生成する敵対的生成ネットワーク「pix2pix」を使って、ベイヤー画像からカラー画像を生成するデモザイクを試してみます。

デモザイク処理とは

デジタルカメラのイメージセンサーは、各ピクセルに当たる光の「色」を直接検出することはできません。センサーが検出できるのは各ピクセルに当たる光の「明るさ」情報です。色情報を得るためには、画素の前に特定の色のみを透過するカラーフィルターを配置しています。
カラーフィルタの配色や配置にはさまざまなパターンがありますが、多くのデジタルカメラでは、ベイヤーフィルタと呼ばれるカラーフィルタが採用されています。
ベイヤーフィルタ(wikipedia)

320px-Bayer_pattern_on_sensor.svg.png

ベイヤーフィルタでは、1画素内の情報は、赤、緑、青のいづれかのチャンネルの情報のみです。このベイヤー画像からフルカラー画像を得るためには、欠損している色情報を周辺のピクセルから予測する必要があります。

この処理をデモザイク処理と呼びます。

デモザイク処理のアルゴリズムは今までさまざまな方法が提案されています。もっともシンプルなアルゴリズムは、線形補間を用いたデモザイク処理です。
このアルゴリズムでは、欠損した色情報を隣接ピクセルから線形補間により求めます。たとえば青の画素位置において、緑色の情報を予想するには、隣接した上下左右の緑画素の信号の平均を求めます。

この方法は、輝度や色が一定の領域や、滑らかに変化する領域であれば、うまくいきます。しかし明るさや色が急激に変化する領域では、画像のボケ(高周波成分の喪失)や、色の滲み(偽色)などの不自然な画像を生成します。

kodim11-bayer.png kodim11-bilinear.png kodim11-targets.png
左:ベイヤー画像 中央:線形補間 右:原画像

pix2pix-tensorflow

今回は、「pix2pix」を使用してデモザイクアルゴリズムを学習させてみます。
「pix2pix」は、いくつかのプラットフォームで実装されていますが、今回はtensorflow版の、「pix2pix-tensorflow」を使用しました。
affinelayer/pix2pix-tensorflow

データセットの準備

「pix2pix」で学習するためには、入力画像であるベイヤー画像と、学習目標画像であるフルカラー画像のペアが枚数必要です。本物のベイヤー画像を準備するのは大変なので、今回は、Web上のフルカラー画像から、擬似的なベイヤー画像を生成します。
フルカラー画像は、以下の画像データを利用しました。

擬似ベイヤー画像生成

実際のベイヤー画像からフルカラー画像への現像処理では、デモザイク処理だけでなく、ホワイトバランス処理や色再現補正処理、エッジ強調処理、トーンマッピング処理などのさまざまな処理によってフルカラー画像を生成します。フルカラー画像から、「リアル」な疑似ベイヤー画像を得るためには、これらの逆変換処理を行う必要があります。これらの処理はカメラメーカによって異なるため、正確なパラメータを得ることは難しいでしょう。今回は、これらの特性は一切無視して、単純にフルカラー画像を「モザイキング」します。

colour-demosaicingを参考に、OpenCVのカラーチャンネルオーダ(BGR)に変更しました。また、参照元のベイヤー画像はシングルチャンネルの画像ですが、このコードでは、3チャンネルのベイヤー画像を出力します。欠損した色情報は0として出力します。


def masks_CFA_Bayer(shape, pattern='RGGB'):
    pattern = pattern.upper()
    channels = dict((channel, np.zeros(shape)) for channel in 'BGR')
    for channel, (y, x) in zip(pattern, [(0, 0), (0, 1), (1, 0), (1, 1)]):
        channels[channel][y::2, x::2] = 1
    return tuple(channels[c].astype(bool) for c in 'BGR')

def mosaicing_CFA_Bayer(BGR, pattern='RGGB'):
    B, G, R = cv2.split(BGR)
    B_m, G_m, R_m = masks_CFA_Bayer(BGR.shape[0:2], pattern)
    CFA = cv2.merge((B * B_m, G * G_m, R * R_m))
    return CFA

また、「pix2pix-tensorflow」では、画像サイズは256x256で固定されています。これに合わせて、画像の中心部256x256の領域を切り出します。また、「pix2pix-tensorflow」では、入力画像と目標画像を左右に結合して、1枚の画像として学習させます。左側にベイヤー画像、右側にフルカラー画像を配置して、結合します。

学習

準備したデータセットを用いて学習します。
「pix2pix-tensorflow」で学習する上で注意すべきパラメータとしては、

  • 学習時にスケーリングを行わない(--scale_size 256)
    デフォルトでは、学習時に、286x286に画像をスケーリングしてから中央部256x256をクロッピングしています。
    今回の用途では、この処理の副作用が無視できないため、スケーリングをオフにします。
  • 学習時に左右フリップしない(--no_flip)
    ベイヤー画像では左右フリップすると、カラーフィルタのパターンが反転します。(RGGBがGRBGになる)
    です。

今回は、約1000枚の学習データに対して、1000エポック学習させました。

評価

学習したパラメータをもちいて、評価データセット(Kodak)を現像します。
また、比較のために、線形補間法、MalvarDFDPDで現像します。これらのアルゴリズムは、colour-demosaicingで実装されています。

定量評価のために、各アルゴリズムでのデモザイク処理と原画像との、PSNRを算出します。

bilinear malvar ddfapd pix2pix
kodim01 27.83 34.08 37.68 36.76
kodim02 34.06 37.92 42.29 38.42
kodim03 34.40 40.01 42.60 37.90
kodim04 37.01 43.48 46.37 39.26
kodim05 27.47 35.93 39.17 35.74
kodim06 28.32 34.58 38.24 36.55
kodim07 32.73 39.97 42.31 37.58
kodim08 27.86 34.64 38.18 35.71
kodim09 32.93 39.76 45.52 38.46
kodim10 35.95 44.71 46.40 38.21
kodim11 28.20 34.84 37.67 36.52
kodim12 31.89 38.86 43.46 37.15
kodim13 26.66 33.56 35.20 35.55
kodim14 29.67 35.04 37.18 35.29
kodim15 33.72 39.02 39.96 37.97
kodim16 32.39 39.15 43.21 38.50
kodim17 33.92 41.16 44.04 38.41
kodim18 28.54 35.50 36.56 35.75
kodim19 28.94 35.46 41.43 36.79
kodim20 30.69 39.13 41.72 33.45
kodim21 29.45 36.13 38.86 36.48
kodim22 30.62 36.31 39.14 36.08
kodim23 34.49 39.79 44.46 37.82
kodim24 32.04 38.39 39.62 37.01
average 31.24 37.81 40.89 36.97

24枚のPSNR平均で出力結果を比較してみます。
bilinearと比較すると、約5.7dBの画質改善となっていますが、malvarと比較すると約1dB、ddfapdと比較すると約3.9dBほどの画質劣化となっています。

"lighthouse(kodim18)"の出力画像を比較してみます

kodim19-bilinear.png kodim19-pix2pix1000.png kodim19-targets.png 
kodim18 左:線形補間(28.54dB) 中央:pix2pix(35.75dB) 右:原画像

bilinearでは、右下の柵の部分にチェッカー状の偽色が発生しています。また、灯台の壁部分も元画像と比較すると、ボケて見えます。
pix2pixの出力結果は、ボケや、チェッカー状の偽色は発生していません。

学習回数増加による性能改善

定量評価では、pix2pixでのdemosaicの出力結果は、既存アルゴリズム(malvar, ddfapd)と比較して劣っていますので、改善を試みます。
単純に、学習時のエポック数を2000まで増やしてみます。

bilinear malvar ddfapd pix2pix
kodim01 27.83 34.08 37.68 39.59
kodim02 34.06 37.92 42.29 40.03
kodim03 34.40 40.01 42.60 40.44
kodim04 37.01 43.48 46.37 45.11
kodim05 27.47 35.93 39.17 36.71
kodim06 28.32 34.58 38.24 39.13
kodim07 32.73 39.97 42.31 40.46
kodim08 27.86 34.64 38.18 36.80
kodim09 32.93 39.76 45.52 42.10
kodim10 35.95 44.71 46.40 44.47
kodim11 28.20 34.84 37.67 38.14
kodim12 31.89 38.86 43.46 39.72
kodim13 26.66 33.56 35.20 37.28
kodim14 29.67 35.04 37.18 36.57
kodim15 33.72 39.02 39.96 39.68
kodim16 32.39 39.15 43.21 43.23
kodim17 33.92 41.16 44.04 43.04
kodim18 28.54 35.50 36.56 36.44
kodim19 28.94 35.46 41.43 38.71
kodim20 30.69 39.13 41.72 27.97
kodim21 29.45 36.13 38.86 30.42
kodim22 30.62 36.31 39.14 37.83
kodim23 34.49 39.79 44.46 41.29
kodim24 32.04 38.39 39.62 39.92
average 31.24 37.81 40.89 38.96

エポック数1000の時点の出力と比較して、平均で2dBほど改善し、malvarとの比較では約1dBほど画質改善となりました。
ddfapdとの比較では、まだ逆転には至らず、約2dBほど劣っています。

既存手法との組み合わせによる性能改善

既存手法との組み合わせによって、性能改善を試みます。ベイヤー画像を直接pix2pixで処理するのではなく、線形補間法で補間した画像を入力画像として使用してみました。
こちらも1000エポック学習してみます。

bilinear malvar ddfapd outputs
kodim01 27.83 34.08 37.68 39.87
kodim02 34.06 37.92 42.29 39.71
kodim03 34.40 40.01 42.60 40.23
kodim04 37.01 43.48 46.37 45.38
kodim05 27.47 35.93 39.17 36.75
kodim06 28.32 34.58 38.24 39.44
kodim07 32.73 39.97 42.31 40.18
kodim08 27.86 34.64 38.18 37.29
kodim09 32.93 39.76 45.52 42.43
kodim10 35.95 44.71 46.40 45.19
kodim11 28.20 34.84 37.67 38.06
kodim12 31.89 38.86 43.46 40.99
kodim13 26.66 33.56 35.20 37.33
kodim14 29.67 35.04 37.18 36.50
kodim15 33.72 39.02 39.96 39.75
kodim16 32.39 39.15 43.21 42.62
kodim17 33.92 41.16 44.04 43.45
kodim18 28.54 35.50 36.56 36.63
kodim19 28.94 35.46 41.43 39.30
kodim20 30.69 39.13 41.72 35.71
kodim21 29.45 36.13 38.86 39.32
kodim22 30.62 36.31 39.14 37.83
kodim23 34.49 39.79 44.46 41.40
kodim24 32.04 38.39 39.62 40.04
average 31.24 37.81 40.89 39.81

bilinearと比較すると、約8.6dBの画質改善、malvarとの比較では約2dBほどの画質改善になっています。
ddfapdとの比較では、まだ逆転には至らず、約1dBほど劣っています。

比較画像
kodim07-bilinear.png kodim07-outputs.png kodim07-targets.png
kodim07 左:線形補間(32.73dB)中央:pix2pix(40.18dB) 右:原画像

kodim08-bilinear.png kodim08-outputs.png kodim08-targets.png
kodim08 左:線形補間(27.86dB)中央:pix2pix(37.29dB) 右:原画像

kodim11-bilinear.png kodim11-outputs.png kodim11-targets.png
kodim11 左:線形補間(28.20dB)中央:pix2pix(38.06dB)右:原画像

kodim19-bilinear.png kodim19-outputs.png kodim19-targets.png
kodim19 左:線形補間(28.94dB) 中央:pix2pix(39.30dB) 右:原画像

まとめ

pix2pixを、ベイヤー画像からカラー画像への変換に応用してみました。人間が考案したさまざまなアルゴリズムと比較しても、遜色のない画質の画像を得ることができました。さらなる画質改善を行うためには、ジェネレータやディスクミネータの損出関数の見直しや、ネットワーク構成の見直しなどが考えられます。しかし、それらの工夫よりも、”より良質なデータセット”で”より多くのエポック数で学習”した方が、より良い結果が得られるかもしれません。

また、今回はデモザイク処理にフォーカスして学習させました。CNNを使った例では、デモザイク処理とデノイズ処理とを融合させた例などなどもあります。
Joint demosaicing and denoising of RAW images with a CNN
こちらは、損出関数としてL1normとSIMMの混合指標によりCNNを学習しており、敵対的生成ネットワークではありませんが、デモザイク処理とデノイズ処理の融合にもpix2pixは応用できるでしょう。今後試してみたいと思います。

1
2
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
1
2

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?