二元稀疏性损失

Loss for binary sparsity

我的网络输出有二进制图像(如下图)。我需要'1'彼此远离(不连接),以便它们形成稀疏的二进制图像(没有白色斑点)。有点像椒盐噪音。我正在寻找一种方法来定义损失(在 pytorch 中),该损失将根据 '1' 的密度进行惩罚。

谢谢。

这取决于您生成所述图像的方式。由于神经网络必须通过反向传播进行训练,我很确定你的二进制图像不是你的神经网络的直接输出(即不是你正在应用损失的东西),因为梯度不能通过二进制(离散)变量。我怀疑你做了像像素 binary cross entropy 或类似的东西,然后是阈值。

我假设你的代码是这样工作的:你密集地回归实数值,然后应用阈值,可能使用 sigmoid[-inf, inf] 映射到 [0, 1]。如果是这样,您可以执行以下操作。构建一个在中心 0 而在其他地方 1 的卷积核,其大小与您希望 "sparsity gaps" 的大小有关。

kernel = [
    [1, 1, 1, 1, 1]
    [1, 1, 1, 1, 1]
    [1, 1, 0, 1, 1]
    [1, 1, 1, 1, 1]
    [1, 1, 1, 1, 1]
]

然后您将 sigmoid 应用于您的实值输出以将其压缩为 [0, 1]:

squashed = torch.sigmoid(nn_output)

然后您将 squashedkernel 进行卷积,这将为您提供非零邻居的宽松数量。

neighborhood = nn.functional.conv2d(squashed, kernel, padding=2)

你的损失将是 squashed 中每个像素值与 neighborhood 中相应值的乘积:

sparsity_loss = (squashed * neighborhood).mean()

如果你认为这种损失适用于你的二值图像,对于给定的像素 p 当且仅当 p 和它的至少一个邻居的值都为 1 时,它才会为 1否则为 0。由于我们将其应用于 [0, 1] 范围内的非二进制数字,因此它将是该数字的可微分近似值。

请注意,我在上面的代码中遗漏了一些细节(例如正确重塑 kernel 以使用 nn.functional.conv2d)。