pytorch学習シリーズ(5):単一チャネル階調図の保存(大ピット)

6925 ワード

pytorchのtorchvisionでは本格的な階調画像を保存できません


画像関連の深さ学習モデルでは、訓練中の画像を保存したり、テストして得られた画像(特にノイズ除去、超解像度、圧縮再構成などの低レベルの視覚タスク)をテストしたりする必要がある場合があり、一般的には、画像保存(torchvision.utilsのsave_image()関数)を以下の方法で行う.
torchvision.utils.save_image(output.data,'%d.bmp'% (idx), padding=0)

しかし、この方式ではRGBカラー画像しか保存できず、ネットワークの出力が単一チャネル階調画像であれば、この関数は依然として3つのチャネルを出力し、各チャネルの数値は同じである「擬似階調画像」であり、視覚効果から区別は見えないが、画像のメモリは通常の状況より2倍大きい.では、本当の階調画像をどのように保存しますか?まずはsave_へimage()関数を探究する:
def save_image(tensor, filename, nrow=8, padding=2,
               normalize=False, range=None, scale_each=False, pad_value=0):
    """Save a given Tensor into an image file.

    Args:
        tensor (Tensor or list): Image to be saved. If given a mini-batch tensor,
            saves the tensor as a grid of images by calling ``make_grid``.
        **kwargs: Other arguments are documented in ``make_grid``.
    """
    from PIL import Image
    grid = make_grid(tensor, nrow=nrow, padding=padding, pad_value=pad_value,
                     normalize=normalize, range=range, scale_each=scale_each)
    # Add 0.5 after unnormalizing to [0, 255] to round to nearest integer
    ndarr = grid.mul_(255).add_(0.5).clamp_(0, 255).permute(1, 2, 0).to('cpu', torch.uint8).numpy()
    im = Image.fromarray(ndarr)
    im.save(filename)

画像処理モジュールPILが使用され、make_が使用されていることがわかるgrid()関数を処理しmake_に転送grid()関数には、コードが表示されます.
if tensor.dim() == 4 and tensor.size(1) == 1:  # single-channel images
        tensor = torch.cat((tensor, tensor, tensor), 1)

これは、テンソルのチャネルが1であれば、出力が3つの同じテンソルをつなぎ合わせて3チャネル画像を形成することを示す.問題発見.

解決策


save_イメージ()関数では、最後の保存画像のコードを次のように変更します.
im.convert('L').save(filename)

すなわち、階調図に変換して保存する.


カラーマップの階調マップの原理は、一般的に次の式を使用して変換されます.
Gray = 0.29900 * R + 0.58700 * G + 0.11400 * B

make_grid()関数は3チャネル同じ擬似階調画像を生成するので,上記式で計算した階調マップはネットワーク出力のテンソルに合致し,損失は生じなかった.