首页
学习
活动
专区
圈层
工具
发布
首页
学习
活动
专区
圈层
工具
MCP广场
社区首页 >问答首页 >基于稀疏标签的AI分类技术

基于稀疏标签的AI分类技术
EN

Data Science用户
提问于 2022-06-14 02:27:34
回答 1查看 143关注 0票数 1

我想要创建一个AI来用大量的标签(1000+标签)对图像进行分类。然而,数据集中的标签是正确的,但每个图像没有完全标签。这意味着每个图像的标签都是正确的,但不完整。

例如,图像可能只有A类、B类和C类的标签,但也适合标签D和E。这意味着图像可能适合标签,尽管没有正确地分配它们。

我需要一个AI/培训方法,通过给予更多的权重来呈现标签,减少对不存在的标签的权重,从而解释这些不准确的地方。

有办法这样做吗?

EN

回答 1

Data Science用户

发布于 2022-06-14 17:19:27

我需要一个AI/培训方法,通过给予更多的权重来呈现标签,减少对不存在的标签的权重,从而解释这些不准确的地方。

这是一个多标签分类问题。您可以尝试的一件事是将问题处理为N同步二进制分类问题,其中N是类的数量。然后,您可以定义一个自定义损失函数,该函数比负数更高地加权正示例。

这是一个具体的例子在角星。首先,我们将定义一个神经网络,它将图像作为输入,并具有N乙状结肠输出,每个类一个。

代码语言:javascript
运行
复制
from tensorflow.keras import Sequential
from tensorflow.keras.layers import Conv2D
from tensorflow.keras.layers import MaxPooling2D

labels = ["a", "b", "c", . . .]

INPUT_SHAPE = (256, 256, 1)
NUM_CLASSES = len(labels)

model = models.Sequential()

model.add(
    layers.Conv2D(32,(5,5),activation=’relu’, input_shape=INPUT_SHAPE)
)
model.add(layers.MaxPooling2D((2, 2)))

model.add(layers.Conv2D(64, (5, 5), activation=’relu’))
model.add(layers.MaxPooling2D((2, 2)))

model.add(layers.Flatten())
model.add(layers.Dense(NUM_CLASSES, activation=’sigmoid’))

再次,我想强调的是,最后一层具有sigmoid激活,而不是softmax,就像您在多类分类中看到的那样。这意味着模型将为每个类输出0到1之间的概率。

接下来,我们需要一个自定义丢失函数,它比负/缺失标签更高地衡量正标签。对于一般的多标号问题,常用的是二元交叉熵损失.它的定义是:

L = -\sum_{c=1}^{N}[y_c log(p_c) + (1 - y_c) log(1 - p_c)]

哪里

  • N是类的数量
  • 如果类标签y_c是示例的正确分类,则为二进制指示符(0或1)。
  • p_c是该示例属于c类(即c类的模型输出)的预测概率。

这是很容易修改这个损失函数,以权衡正负两方面的例子。只需将系数添加到损失的正分量和损失的负部分:

L = -\sum_{c=1}^{N}[w_p * y_c log(p_c) + w_n * (1 - y_c) log(1 - p_c)]

哪里

  • w_p是正示例的权重。
  • w_n是负示例的权重。

从技术上讲,w_pw_n是应该在训练期间调优的超参数。但就我们的目的而言,假设是w_p = 1w_n = 0.5。现在,我们已经准备好定义自定义丢失函数:

代码语言:javascript
运行
复制
from tensorflow.keras import backend as K

w_p = 1.0
w_n = 0.5

def custom_loss(y_true, y_pred):
    '''  Weighted multi-label cross-entropy

    Args:
        y_true: true labels, one-hot-encoded
        y_pred: labels predicted by the model 
    '''
    loss = float(0)
    
    for i, label in enumerate(labels):
        positive_term = w_p * y_true[i] * K.log(y_pred[i] + K.epsilon())
        negative_term = w_n * (1 - y_true[i]) * K.log(1 - y_pred[i] + K.epsilon())
        loss -= (positive_term + negative_term)
    return loss

最后一步是用这个损失函数编译和训练模型:

代码语言:javascript
运行
复制
from tf.keras.optimizers import Adam
from tensorflow.keras.preprocessing.image import ImageDataGenerator

N_EPOCHS = 100

my_data_generator = ImageDataGenerator(rescale=1./255)
target_size = INPUT_SHAPE[0:2]

train_generator = train_datagen.flow_from_directory(
    'data/train/',
    target_size=target_size,
    batch_size=32
)

model.compile(
    optimizer=Adam(),
    loss=custom_loss
)

history = model.fit(
    my_data_generator,
    epochs=N_EPOCHS,
)

塔达!一种具有自定义丢失功能的卷积网络,它使现在的标签具有更大的权重。显然,您可以重新配置网络架构和正负权重,以更好地适应您的用例。

票数 -1
EN
页面原文内容由Data Science提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://datascience.stackexchange.com/questions/111800

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档