Может ли кто-нибудь помочь мне преобразовать следующую функцию потери PyTorch в функцию потери Keras? Первая часть - это метри c, а затем соответствующая ей функция суррогатных потерь. Я не нашел точного соответствия между каждой функцией PyTorch с функцией Keras. Я думаю, что опытному инженеру понадобится всего 2 минуты для этого преобразования. Спасибо заранее за вашу помощь. Эта функция потерь была получена из следующей статьи: https://arxiv.org/abs/2003.07311. На последних страницах вы можете найти эту реализацию.
# clDice measure
from skimage.morphology import skeletonize
import numpy as np
def cl_score(v, s):
return np.sum(v ∗ s) / np.sum(s)
def clDice(v_p, v_l):
tprec = cl_score(v_p, skeletonize(v_l))
tsens = cl_score(v_l, skeletonize(v_p))
return 2 ∗ tprec ∗ tsens / (tprec + tsens)
# clDice loss
import torch.nn.functional as F
def soft_erode(img):
p1 = −F.max_pool2d(−img, (3, 1), (1, 1), (1, 0))
p2 = −F.max_pool2d(−img, (1, 3), (1, 1), (0, 1))
return torch.min(p1, p2)
def soft_dilate(img):
return F.max_pool2d(img, (3, 3), (1 ,1), (1, 1))
def soft_open(img):
return soft_dilate(soft_erode(img))
def soft_skel(img, iter):
img1 = soft_open(img)
skel = F.relu(img−img1)
for j in range (iter):
img = soft_erode(img)
img1 = soft_open(img)
delta = F.relu(img−img1)
skel = skel + F.relu(delta − skel ∗ delta)
return skel
def soft_clDice(v_p, v_l, iter = 50, smooth = 1):
s_p = soft_skel(v_p, iter)
s_l = soft_skel(v_l, iter)
tprec = ((s_p ∗ v_l).sum() + smooth) / (s_p.sum() + smooth)
tsens = ((s_l ∗ v_p).sum() + smooth) / (s_l.sum() + smooth )
return 2 ∗ tprec ∗ tsens / (tprec + tsens)
До сих пор я создал следующее:
import keras
def soft_clDice_loss(gt, pr, iter=50,smooth=1):
def soft_erode(img):
p1 = −keras.backend.pool2d(−img, (3, 1), (1, 1), (1, 0))
p2 = −keras.backend.pool2d(−img, (1, 3), (1, 1), (0, 1))
return keras.backend.min(p1, p2)
def soft_dilate(img):
return keras.backend.pool2d(img, (3, 3), (1 ,1), (1, 1))
def soft_open(img):
img = soft_erode(img)
img = soft_dilate(img)
return img
def soft_skel(img, iters):
img1 = soft_open(img)
skel = keras.backend.relu(img−img1)
for j in range(iter):
img = soft_erode(img)
img1 = soft_open(img)
delta = keras.backend.relu(img-img1)
intersect = keras.backend.dot(skel, delta)
skel += keras.backend.relu(delta-intersect)
return skel
def soft_clDice_loss(iters = 50):
def loss(y_true, y_pred):
smooth = 1.
skel_pred = soft_skel(y_pred, iters)
skel_true = soft_skel(y_true, iters)
pres = (keras.backend.sum(keras.backend.dot(skel_pred, y_true)[:,1:,:,:,:])+smooth)/(keras.backend.sum(skel_pred[:,1:,:,:,:])+smooth)
rec = (keras.backend.sum(keras.backend.dot(skel_true, y_pred)[:,1:,:,:,:])+smooth)/(keras.backend.sum(skel_true[:,1:,:,:,:])+smooth)
cl_dice = 1.- 2.0*(pres*rec)/(pres+rec)
return cl_dice
return loss