Python TensorFlow/Keras模型在尝试预测时出错,引用了形状不匹配,尽管我提供的形状似乎正确
我不确定我是否理解不了输入张量的概念,或者我是否用错误的输入形状训练了模型,或者我是否需要以某种方式指定图像 模型构建如下:Python TensorFlow/Keras模型在尝试预测时出错,引用了形状不匹配,尽管我提供的形状似乎正确,python,image,opencv,tensorflow,keras,Python,Image,Opencv,Tensorflow,Keras,我不确定我是否理解不了输入张量的概念,或者我是否用错误的输入形状训练了模型,或者我是否需要以某种方式指定图像 模型构建如下: ... import all the usual libraries - TF, Keras, Numpy, OpenCV etc. ... _MODEL_DIMENSION = 128 def create_model_for_dimension(dimension): model = Sequential() if dimension >= 2
... import all the usual libraries - TF, Keras, Numpy, OpenCV etc. ...
_MODEL_DIMENSION = 128
def create_model_for_dimension(dimension):
model = Sequential()
if dimension >= 256:
model.add(Conv2D(256, kernel_size=(5, 5), input_shape=(dimension, dimension, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
if dimension >= 128:
model.add(Conv2D(128, kernel_size=(3, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
…… more convolution layers ……..
…………………………………………..
……………………………………………..
model.add(Flatten())
……… More layers …………………
……………………………………………..
……………………………………………..
model.add(Dense(2))
model.add(Activation('sigmoid'))
model.compile(loss='categorical_crossentropy',
optimizer=tf.keras.optimizers.Adam(),
metrics=['accuracy'])
return model
train_datagen = ImageDataGenerator(
rotation_range=10,
width_shift_range=0.2,
height_shift_range=0.2,
rescale=1./255,
shear_range=0.2,
zoom_range=1.2,
horizontal_flip=True,
vertical_flip=True,
fill_mode='nearest')
train_generator = train_datagen.flow_from_directory(
train_data_directory,
target_size=(_MODEL_DIMENSION, _MODEL_DIMENSION),
batch_size=_BATCH_SIZE,
class_mode='categorical')
……… validate_generator …………………
……………………………………………………
………………………………………………………
……… test_generator ………………………
………………………………………………………
………………………………………………………
……… train and save the model ……
ValueError: Input 0 of layer sequential is incompatible with the layer: expected ndim=4, found ndim=3. Full shape received: [32, 128, 3]
当我训练并使用它预测目录中的图像时,一切都正常(或者至少看起来正常)。但我随后尝试以以下方式输入图像,而不使用ImageDataGenerator:
首先,我使用OpenCV读取图像(我希望使用OpenCV进行其他处理,所以我不使用PIL)
然后我使用范围裁剪图像
cropped_area = snapshot[y[0]:y[1], x[0]:x[1]]
然后我使用如下模型进行评分。我还尝试了np.array转换以外的变体
score_val = model.predict(np.array(cropped_area/255.0))
此时会出现如下错误:
... import all the usual libraries - TF, Keras, Numpy, OpenCV etc. ...
_MODEL_DIMENSION = 128
def create_model_for_dimension(dimension):
model = Sequential()
if dimension >= 256:
model.add(Conv2D(256, kernel_size=(5, 5), input_shape=(dimension, dimension, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
if dimension >= 128:
model.add(Conv2D(128, kernel_size=(3, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
…… more convolution layers ……..
…………………………………………..
……………………………………………..
model.add(Flatten())
……… More layers …………………
……………………………………………..
……………………………………………..
model.add(Dense(2))
model.add(Activation('sigmoid'))
model.compile(loss='categorical_crossentropy',
optimizer=tf.keras.optimizers.Adam(),
metrics=['accuracy'])
return model
train_datagen = ImageDataGenerator(
rotation_range=10,
width_shift_range=0.2,
height_shift_range=0.2,
rescale=1./255,
shear_range=0.2,
zoom_range=1.2,
horizontal_flip=True,
vertical_flip=True,
fill_mode='nearest')
train_generator = train_datagen.flow_from_directory(
train_data_directory,
target_size=(_MODEL_DIMENSION, _MODEL_DIMENSION),
batch_size=_BATCH_SIZE,
class_mode='categorical')
……… validate_generator …………………
……………………………………………………
………………………………………………………
……… test_generator ………………………
………………………………………………………
………………………………………………………
……… train and save the model ……
ValueError: Input 0 of layer sequential is incompatible with the layer: expected ndim=4, found ndim=3. Full shape received: [32, 128, 3]
我的图像的形状是(128,128,3),我做的所有检查似乎都证实了我一直在给它喂食
任何指点都将不胜感激,因为我花了一天的大部分时间试图解决这个问题!谢谢 您设置了
\u MODEL\u DIMENSION=128
这导致了
if dimension >= 128:
model.add(Conv2D(128, kernel_size=(3, 3)))
您没有设置输入形状,因此,根据设置,预期输入将为:
输入形状
带形状的4D张量:(批次、通道、行、列)如果数据_格式为“通道_优先”,或带形状的4D张量:(批次、行、列、列)如果数据_格式为“通道_最后”
您的输入不适合,因此出现错误
预期ndim=4,发现ndim=3
解决方案是定义一个已存在于代码中的输入形状:
if dimension >= 256:
model.add(Conv2D(256, kernel_size=(5, 5), input_shape=(dimension, dimension, 3)))
您的数据缺少批次维度。您的模型需要4D数据,而不是3D数据
您的图像形状应该是
(1128128,3)
这就是问题所在,谢谢。我们学到的经验是,不要通过参数化模型来减少代码行数,尤其是在不同大小的代码处理方式不同的情况下。