Stackaccount1
Stackaccount1

Reputation: 149

Keras Tensorflow and Open CV Error for Input Variable

Receiving ValueError: Input 0 of layer sequential_14 is incompatible with the layer: : expected min_ndim=4, found ndim=3. Full shape received: [None, 48, 3]

Although my image shape just printed is the correct size (48, 48, 3)

I have tried batch_input_shape with (none,48,48,3

My keras model:

model = Sequential([
        Conv2D(filters=32,kernel_size=(3,3), activation='relu', padding = 'same', input_shape=(48, 48, 3),
        MaxPool2D(pool_size=(2, 2), strides=2),
        Conv2D(filters=64, kernel_size=(3, 3), activation='relu', padding = 'same'),
        MaxPool2D(pool_size=(2, 2), strides=2),
        Flatten(),
        Dense(units=2, activation='softmax'),
])

Model Setup Python

from keras.models import load_model
new_model = load_model('/home/user/Downloads/filehere.h5')
new_model.summary()

class trueoruntruemodel(object):

    options = ["true", "untrue"]

    def __init__(self, new_model):
        self.loaded_model = new_model

    def predict_true(self, img):
        self.preds = self.loaded_model.predict(img)
        return trueoruntruemodel.options[np.argmax(self.preds)]


Camera Setup File

import cv2
from modelsetup import trueoruntruemodel
from modelsetup import new_model
import numpy as np
model = trueoruntruemodel(new_model)
font = cv2.FONT_HERSHEY_SIMPLEX

class VideoCamera(object):
    def __init__(self):
        self.video = cv2.VideoCapture(0)

    def __del__(self):
        self.video.release()

    def get_frame(self):
        _, fr = self.video.read()
        print(fr.shape)
        roi = cv2.resize(fr, (48, 48))
        print(roi.shape) # this is coming out correctly as 48,48,3
        pred = model.predict_true(roi)
        cv2.putText(fr, pred, (x,y), font, 1, (46, 46, 0), 2)

        _, jpeg = cv2.imencode('.jpg', fr)
        return jpeg.tobytes()

Flask Stream File

from flask import Flask, render_template, Response
from Camera import VideoCamera

app = Flask(__name__)

@app.route('/')
def index():
    return render_template('index.html')

def gen(camera):
    while True:
        frame = camera.get_frame()
        yield (b'--frame\r\n'
               b'Content-Type: image/jpeg\r\n\r\n' + frame + b'\r\n\r\n')

@app.route('/video_feed')
def video_feed():
    return Response(gen(VideoCamera()),
                    mimetype='multipart/x-mixed-replace; boundary=frame')

if __name__ == '__main__':
    app.run(host='0.0.0.0', debug=True)

Upvotes: 1

Views: 146

Answers (2)

Francesco Cariaggi
Francesco Cariaggi

Reputation: 838

You have to add the batch dimension to your image before feeding it to the model. Use tf.expand_dims(img, axis=0)

Upvotes: 2

maciek97x
maciek97x

Reputation: 7062

You should pass a batch instead of single input - shape of roi is (48,48,3), but should be (_,48,48,3). One way to achieve it is to use numpy.expand_dims

pred = model.predict_true(np.expand_dims(roi, axis=0))

Upvotes: 2

Related Questions