【问题标题】:Received a label value of 1 which is outside the valid range of [0, 1) - Python, Keras收到的标签值 1 超出 [0, 1) 的有效范围 - Python,Keras
【发布时间】:2021-08-25 13:05:34
【问题描述】:

我正在使用具有 tensorflow 背景的 keras 开发一个简单的 cnn 分类器。

def cnnKeras(training_data, training_labels, test_data, test_labels, n_dim):
  print("Initiating CNN")
  seed = 8
  numpy.random.seed(seed)
  model = Sequential()
  model.add(Convolution2D(64, 1, 1, init='glorot_uniform', 
   border_mode='valid',input_shape=(16, 1, 1), activation='relu'))
  model.add(MaxPooling2D(pool_size=(1, 1)))
  model.add(Convolution2D(32, 1, 1, init='glorot_uniform', 
   activation='relu'))
  model.add(MaxPooling2D(pool_size=(1, 1)))
  model.add(Dropout(0.25))
  model.add(Flatten())
  model.add(Dense(128, activation='relu'))
  model.add(Dropout(0.5))
  model.add(Dense(64, activation='relu'))
  model.add(Dense(1, activation='softmax'))
  # Compile model
  model.compile(loss='sparse_categorical_crossentropy',
              optimizer='adam', metrics=['accuracy'])
  model.fit(training_data, training_labels, validation_data=(
    test_data, test_labels), nb_epoch=30, batch_size=8, verbose=2)

  scores = model.evaluate(test_data, test_labels, verbose=1)
  print("Baseline Error: %.2f%%" % (100 - scores[1] * 100))
  # model.save('trained_CNN.h5')
  return None

这是一个二元分类问题,但我不断收到消息Received a label value of 1 which is outside the valid range of [0, 1),这对我来说没有任何意义。有什么建议吗?

【问题讨论】:

    标签: python machine-learning keras


    【解决方案1】:

    Range [0, 1) 表示 0 到 1 之间的每个数字,不包括 1。所以 1 不是 [0, 1) 范围内的值。

    我不是 100% 确定,但问题可能是由于您选择的损失函数。对于二元分类,binary_crossentropy 应该是更好的选择。

    【讨论】:

      【解决方案2】:

      在最后一个密集层中,您使用了model.add(Dense(1, activation='softmax'))。这里 1 将其值从 [0, 1) 限制为将其形状更改为最大输出标签。例如,您的输出来自标签[0,7),然后使用model.add(Dense(7, activation='softmax'))

      【讨论】:

      • 根据文档(keras.io/layers/core),这里的 1 是输出维度(等级)而不是输出范围。
      【解决方案3】:

      稀疏分类交叉熵的特点

      损失函数 sparse_categorical_crossentropy 将分类器上下文中的最后一层解释为每个可能类的一组概率,并将输出值解释为 类的编号。 (Tensorflow/Keras documentation 更详细一点。)因此,输出层中的 x 个神经元与 0 到 x-1 范围内的输出值进行比较;并且在输出层中只有一个神经元是一个没有意义的“一元”分类器。

      如果是分类任务,希望输出数据的形式为 0 到 x-1,那么可以保持稀疏分类交叉熵,但是需要将输出层的神经元个数设置为你有的课。或者,您可以将输出编码为 one-hot 向量,并使用分类交叉熵损失函数而不是稀疏分类交叉熵。

      如果它不是分类任务,并且您想像回归一样预测任意实数值,那么分类交叉熵根本就不是合适的损失函数。

      【讨论】:

      • 所以,如果要预测第 6 个数字,其中训练数据是 [1,2,3,4,5] 并且有一个类别: [6] ,您的分类是什么方法?我会假设保持分类交叉熵,在这种特定情况下,“一元”分类器可能是有意义的。
      • 如果它是一个分类任务,那么您正在学习(即调整参数)一个函数,其中可能的输出集(即函数的范围,在什么函数的技术数学定义中) is) 是类别列表。如果只有一个类别,这是范围由单个值组成的退化形式,并且您有一个函数,根据定义,该函数不能输出除该单个类别之外的任何内容,无论给出什么输入,无论它是否不管有没有受过训练,它总是输出技术上唯一可行的答案。
      • 所以不,一元分类器永远没有意义,只是作为退化边缘情况的一个例子,在技术上可能算作“可学习函数”。该评论似乎说明了对分类含义的基本误解 - 分类器将尝试预测(预定义的)可能答案之一。如果只有一个类别,则没有什么可预测的,不可能给出错误的答案,因为不可能有其他答案 - “有一个类别:[6]”字面意思是您正在做出明确的假设 [6]无论如何都是唯一可能的输出。
      • 并且“如果想预测第 6 个数字,其中训练数据是 [1,2,3,4,5] 并且有一个类别:[6]” - 如果我是将其理解为预测序列中下一个数字的任务(因此它也必须适用于 [11,12,13,14,15]->[16] )然后 no 分类方法将是合适的,因为它(就像预测任意实数或自然数的任何其他任务一样)在很大程度上不是分类问题,它违反了分类问题的核心假设。
      • 这个网站帮我选择了我的损失函数machinelearningmastery.com/…
      【解决方案4】:

      Cray 和 Shaili 的答案是正确的! 我有一系列从 1 到 6 的结果, 和行:

      tf.keras.layers.Dense(6, activation = 'softmax') 
      

      产生了那个错误信息,说事情超出了范围 [0,6)。我曾认为这是一个标签问题(所有值都存在于 训练和验证标签集?),并且正在鞭打它们。

      )

      【讨论】:

        【解决方案5】:

        错误在 [0,4) 范围内,您可以在类(标签)的数量上加一。 例如改变这个:

        layers.Dense(4)
        

        到:

        layers.Dense(5)
        

        **与 [0,1) 相同

        【讨论】:

          【解决方案6】:

          当我有“float”类型的标签时,我遇到了这个问题,将它们转换为“int”,问题就解决了......

          【讨论】:

            【解决方案7】:

            这个问题的另一个潜在答案是关于工作空间。如果它不是其他答案所暗示的逻辑/稀疏性/熵错误,请继续阅读:

            如果您创建了一个工作区来保存模型训练时的数据,如果您使用新样本重新训练数据,旧的工作区数据可能会导致此错误,特别是使用不同数量的文件夹并且使用文件夹作为分类标签。

            示例:

            我训练了我的原始集:

            当我尝试重新训练新的样本集时:

            我收到错误: Received a label value of 3 which is outside the valid range of [0, 3)

            这可能是因为旧样本集的 4 个文件夹的缓存值与新样本集的 3 个文件夹的缓存值导致了某种问题。我所知道的是,一旦我从工作空间中清除了旧信息,然后再次运行它,它就会运行完成。这是多次失败后的孤立更改,所以我确信这是解决问题的原因。

            免责声明:我正在使用 C# 和 ML.NET,但它仍在使用 TensorFlow,这是我们的两个错误产生的地方,所以它绝对应该适用于这个问题。

            【讨论】:

              【解决方案8】:

              对我来说,问题是传递给模型的类数少于数据中的实际类数。因此,模型在大多数情况下预测为 -1,因此误差超出范围。

              【讨论】:

                猜你喜欢
                • 2022-06-29
                • 2021-06-08
                • 2019-11-22
                • 2020-04-03
                • 2019-02-18
                • 1970-01-01
                • 2017-11-25
                • 2021-04-28
                • 2019-04-06
                相关资源
                最近更新 更多