天天看點

tensorflow 中的深度可分離卷積接口 slim.separable_conv2d()

    我在前面的一篇部落格 深入淺出談談深度可分離卷積 中介紹了深度可分離卷積的原理,然後用 tensorflow 實作了下。

    在 tensorflow 中的接口是 slim.separable_conv2d(),接口說明:

def separable_convolution2d(
    inputs,
    num_outputs,
    kernel_size,
    depth_multiplier=1,
    stride=1,
    padding='SAME',
    data_format=DATA_FORMAT_NHWC,
    rate=1,
    activation_fn=nn.relu,
    normalizer_fn=None,
    normalizer_params=None,
    weights_initializer=initializers.xavier_initializer(),
    pointwise_initializer=None,
    weights_regularizer=None,
    biases_initializer=init_ops.zeros_initializer(),
    biases_regularizer=None,
    reuse=None,
    variables_collections=None,
    outputs_collections=None,
    trainable=True,
    scope=None):
  """一個2維的可分離卷積,可以選擇是否增加BN層。
  這個操作首先執行逐通道的卷積(每個通道分别執行卷積),建立一個稱為depthwise_weights的變量。如果num_outputs
不為空,它将增加一個pointwise的卷積(混合通道間的資訊),建立一個稱為pointwise_weights的變量。如果
normalizer_fn為空,它将給結果加上一個偏置,并且建立一個為biases的變量,如果不為空,那麼歸一化函數将被調用。
最後再調用一個激活函數然後得到最終的結果。
  Args:
    inputs: 一個形狀為[batch_size, height, width, channels]的tensor
    num_outputs: pointwise 卷積的卷積核個數,如果為空,将跳過pointwise卷積的步驟.
    kernel_size: 卷積核的尺寸:[kernel_height, kernel_width],如果兩個的值相同,則可以為一個整數。
    depth_multiplier: 卷積乘子,即每個輸入通道經過卷積後的輸出通道數。總共的輸出通道數将為:
num_filters_in * depth_multiplier。
    stride:卷積步長,[stride_height, stride_width],如果兩個值相同的話,為一個整數值。
    padding:  填充方式,'VALID' 或者 'SAME'.
    data_format:資料格式, `NHWC` (預設) 和 `NCHW` 
    rate: 空洞卷積的膨脹率:[rate_height, rate_width],如果兩個值相同的話,可以為整數值。如果這兩個值
任意一個大于1,那麼stride的值必須為1.     
    activation_fn: 激活函數,預設為ReLU。如果設定為None,将跳過。
    normalizer_fn: 歸一化函數,用來替代biase。如果歸一化函數不為空,那麼biases_initializer
和biases_regularizer将被忽略。 biases将不會被建立。如果設為None,将不會有歸一化。
    normalizer_params: 歸一化函數的參數。
    weights_initializer: depthwise卷積的權重初始化器
    pointwise_initializer: pointwise卷積的權重初始化器。如果設為None,将使用weights_initializer。
    weights_regularizer: (可選)權重正則化器。
    biases_initializer: 偏置初始化器,如果為None,将跳過偏置。
    biases_regularizer: (可選)偏置正則化器。
    reuse: 網絡層和它的變量是否可以被重用,為了重用,網絡層的scope必須被提供。
    variables_collections: (可選)所有變量的collection清單,或者是一個關鍵字為變量值為collection的字典。
    outputs_collections: 輸出被添加的collection.
    trainable: 變量是否可以被訓練
    scope: (可選)變量的命名空間。
  Returns:
    代表這個操作的輸出的一個tensor
           

    但是這個接口根據原理來看,我覺得有個缺點,如果設定 depth_multiplier 為1,則變成了單通道的點乘,那這樣是否缺乏了通道間的資訊融合?

    這樣顯然能極大程度減少參數,但是網絡性能也會受到影響,至少對于low-levle 的 cv 任務來說,性能下降很大。

    如有不對請指正。

繼續閱讀