暹罗网络未学习,损失减少但准确性未提高

问题描述

我正在尝试建立一个暹罗网络来检查两条鲸鱼(个体)之间的相似性,我的数据集中有15k张图像,有5k个类别,这就是为什么我选择暹罗并且不使用新类别重新训练模型。这是神经网络架构:

        def contrastiveLoss(y_true,y_pred):
            margin = 1
            return K.mean(y_true * K.square(y_pred) + (1 - y_true) * K.square(K.maximum(margin - y_pred,0)))

        def weightInit(shape,dtype=None):
            return rng.normal(loc = 0.0,scale = 1e-2,size = shape)

        def biasInit(shape,dtype=None):
            return rng.normal(loc = 0.5,size = shape)

        input_shape = (200,200,1)
        left_input = Input(input_shape)
        right_input = Input(input_shape)

        model = Sequential()
        model.add(Conv2D(64,(10,10),activation='relu',input_shape=input_shape,kernel_initializer=weightInit,kernel_regularizer=l2(2e-4)))
        model.add(MaxPooling2D())
        model.add(Conv2D(128,(7,7),kernel_regularizer=l2(2e-4),bias_initializer=biasInit))
        model.add(MaxPooling2D())
        model.add(Conv2D(128,(4,4),bias_initializer=biasInit))
        model.add(MaxPooling2D())
        model.add(Conv2D(256,bias_initializer=biasInit))
        # model.add(BatchNormalization())
        # model.add(Dropout(0.25))
        model.add(Flatten())
        # model.add(Dropout(0.5))
        model.add(Dense(4096,activation="sigmoid",kernel_regularizer=l2(1e-3),bias_initializer=biasInit))

        #call the convnet Sequential model on each of the input tensors so params will be shared
        encoded_l = model(left_input)
        encoded_r = model(right_input)
        #layer to merge two encoded inputs with the l1 distance between them
        L1_layer = Lambda(lambda tensors:K.abs(tensors[0] - tensors[1]))
        #call this layer on list of two input tensors.
        L1_distance = L1_layer([encoded_l,encoded_r])
        prediction = Dense(1,activation='sigmoid',bias_initializer=biasInit)(L1_distance)
        siamese_net = Model(inputs=[left_input,right_input],outputs=prediction)
        optimizer = Adam(0.001)
        siamese_net.compile(loss=contrastiveLoss,optimizer='RMSprop')

我正在尝试像这样运行它:

    #Training loop
evaluate_every = 10 # interval for evaluating on one-shot tasks
loss_every= 10 # interval for printing loss (iterations)
checkOverfitting = 20
batch_size = 32
epochs = 9000
N_way = 5 # how many classes for testing one-shot tasks
n_val = 250 #number of one-shot tasks to validate on
lossHistory = []
val_accHistory = []
print("training")
for i in range(1,epochs):
    (inputs,targets)=dataTrainLoader.getBatch(batch_size)
    (loss)=siamese_net.train_on_batch(inputs,targets)
    lossHistory.append(loss)
    if i % checkOverfitting == 0:
        print("Comparing results with x_train and x_test to check overfitting")
        val_acc_test = dataTrainLoader.test_oneshot(siamese_net,N_way,n_val,X_test,y_test,verbose=True)
        val_acc_train = dataTrainLoader.test_oneshot(siamese_net,X_train,y_train,verbose=True)
        print("Accuracy in train {:.2f},accuracy in test {:.2f} ".format(val_acc_train,val_acc_test))
    elif i % evaluate_every == 0:
        val_acc = dataTrainLoader.test_oneshot(siamese_net,verbose=True)
        val_accHistory.append(val_acc)
    if i % loss_every == 0:
        print("iteration {},loss: {:.2f},val_acc: {:.2f}".format(i,loss,val_acc))

如果需要,我可以补充缺少的功能。 DataTrainLoader是一个类,它为每个时期生成批次(成对),并创建用于测试N_way oneshot的对,并返回正确预测的百分比。

这正在减少损耗,直到某些迭代开始后的某个点如此缓慢地减小为止,例如每2个周期0.01。但是,准确度仍然保持在完整的过山车和非常糟糕的过山车上,包括测试图像和火车图像。我们可以在图形中看到: First loss,then accuracy in test

我已经添加了增强功能,并尝试了诸如更改学习率,更改体系结构,内核,将损失函数设置为binary_crossentropy,batch_size之类的尝试,尝试添加正则化,但它似乎并不过分拟合并检查了参数,通过肉眼和目标比较图像,似乎都是正确的。 我对此无能为力。图像可以用肉眼分辨,也不是不可能的任务。有什么提示,tweeks,我错过了什么错误? 预先感谢您的帮助。

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)

相关问答

错误1:Request method ‘DELETE‘ not supported 错误还原:...
错误1:启动docker镜像时报错:Error response from daemon:...
错误1:private field ‘xxx‘ is never assigned 按Alt...
报错如下,通过源不能下载,最后警告pip需升级版本 Requirem...