【问题标题】:multi-threading, what is wrong with my code多线程,我的代码有什么问题
【发布时间】:2021-07-04 17:08:39
【问题描述】:

我试图在opencv中让我的帧更快,正常使用它很慢,所以我决定在这里问它Make faster videocapture opencv答案是使用多线程让它更快,所以我这样编码

    # The same genderrecognition.py code but with multi-threading to make it faster and fix the the lag of the other one
from tensorflow.keras.preprocessing.image import img_to_array
from tensorflow.keras.models import load_model
import numpy as np
import cv2
import os
import cvlib as cv

# open webcam and initiate the cam
webcam = cv2.VideoCapture(0, cv2.CAP_DSHOW)


# opencv class
class VideoStream:
    def __init__(self):
        # read frame from webcam
        self.status, self.frame = webcam.read()
        webcam.set(cv2.CAP_PROP_FPS, 1000)
        self.frame = cv2.flip(self.frame, 1)

        print("videostream working")


# face detection class
class face_detection:
    def __init__(self):
        # use VideoStream Class variables
        self.videostream = VideoStream()
        self.frame = self.videostream.frame

        # apply face detection
        self.face, self.confidence = cv.detect_face(self.frame)

        # loop through detected faces
        for self.idx, self.f in enumerate(self.face):
            # get the corner point of the rectangle
            self.startX, self.startY = self.f[0], self.f[1]
            self.endX, self.endY = self.f[2], self.f[3]

            cv2.rectangle(self.frame, (self.startX, self.startY), (self.endX, self.endY), (0,255,0), 2)
            self.face_crop = np.copy(self.frame[self.startY:self.endY, self.startX:self.endX])

            if self.face_crop.shape[0] < 10 or self.face_crop.shape[1] < 10:
                continue

            # preprocessing for gender detection model
            self.face_crop = cv2.resize(self.face_crop, (96,96))
            self.face_crop = self.face_crop.astype("float") / 255.0
            self.face_crop = img_to_array(self.face_crop)
            self.face_crop = np.expand_dims(self.face_crop, axis=0)

            GFR()
        print("face_detection working")

# gender recognition class
class GFR:
    def __init__(self):
        self.model = load_model("C:/Users/berna/Desktop/Programming/AI_ML_DL/Projects/FaceGenderRecognition/gender_detection.model")
        self.facedetection = face_detection()

        self.face_crop = self.facedetection.face_crop
        self.classes = ['hombre', 'mujer']
        self.startX, self.startY = self.facedetection.startX, self.facedetection.startY
        self.endX, self.endY = self.facedetection.endX, self.facedetection.endY
        self.frame = self.facedetection.frame

        # apply the gender detection face with the model
        self.conf = model.predict(self.face_crop)[0]

        # get label with max acc
        self.idx = np.argmax(self.conf)
        self.label = self.classes[self.idx]

        self.label = "{}: {:.2f}".format(self.label, self.conf[self.idx] * 100)

        self.Y = self.startY - 10 if self.startY - 10 > 10 else self.startY + 10

        # write label and confidence above the face rectangle
        cv2.putText(self.frame, self.label, (self.startX, self.Y), cv2.FONT_HERSHEY_SIMPLEX,
                    0.7, (0,255,0), 2)

        print("gender recognition working!")


# classes and webcam while loop
gender_detection = GFR()


# loop through frames
while webcam.isOpened():
    VideoStream()
    face_detection()

    # display output
    cv2.imshow("Gender Detection", gender_detection.frame)

    # press "Q" to stop
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

webcam.release()
cv2.destroyAllWindows()

它没有给我任何错误,但与我在另一个问题上的其他代码相比,网络摄像头是打开的,而在这个问题上没有,知道吗?

【问题讨论】:

  • @raspberry_next 也许你知道

标签: python opencv machine-learning


【解决方案1】:

您的 VideoStream 类的 init 看起来不错,但我认为您在 init 中创建 cv2 VideoCapture 对象可能会更好:

self.stream = cv2.VideoCapture(0)

我对 webcam.set() 不是很熟悉,但如果你想加入它,我相信你可以。

这里你已经抓取了初始帧:

self.status, self.frame = webcam.read()

(或使用新的 self.stream 变量):

self.status, self.frame = self.stream.read()

然而,这只会在初始化时抓取一帧,而不是在循环中。要实现一个循环,你必须多做几个类方法。一个是连续获取帧(我添加了一个 self.stopped 属性,虽然它不在您的代码中。有一个真/假停止标志可能是个好主意):

def read_stream(self):
    while not self.stopped:
        (self.grabbed, self.frame) = self.stream.read()

那么如果你想使用多线程,你可以让一个线程指向read_stream方法:

def start(self):
    Thread(target=self.read_stream, args=()).start()
    return self

在开始 CV2 imshow() 循环之前,您必须在 VideoStream 上调用 start() 方法。

video_stream = VideoStream().start().  #<------Here--------

while webcam.isOpened():
    
    face_detection()

    # display output
    cv2.imshow("Gender Detection", gender_detection.frame)

    # press "Q" to stop
    if cv2.waitKey(1) & 0xFF == ord('q'):
        break

希望这有助于让 CV2 显示出来。无论您的 GFR 类还是人脸检测是从 VideoStream 类中获取正确的帧……那是另一回事,我无法调试所有代码。

【讨论】:

  • 我对 ML 和 tensorflow 不太熟悉。所以我得到这个错误,你知道如何解决它吗? “不成功的 TensorSliceReader 构造函数:未能找到 /Gender-Recognition/gender_detection.model/variables/variables 的任何匹配文件”
  • 让网络摄像头和面部检测在新的 gr_faster.py 中工作:github.com/nathanaday/Gender-Recognition/tree/Fix
  • 老兄,抱歉耽搁了,没错,你的新代码让网络摄像头更快!你是火。唯一的问题是性别识别不起作用,但没关系,我可以修复它,你告诉我你得到“无法找到 /Gender-Recognition/gender_detection.model/variables/variables 的任何匹配文件”,是的,它是 bc .model 文件夹我忘了添加一些其他的,但非常感谢兄弟!如果你能解释一下你所做的改变,那就太好了!
  • 很高兴它对你有用。我现在将我的 OCR 放在 github 上并编写自述文件。它本质上是相同的过程——将 OCR 替换为性别检测。希望你能阅读这些文档,看看我在你的代码中做了什么。
  • 正如承诺的那样:代码...github.com/nathanaday/RealTime-OCR
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2012-12-15
  • 2015-06-04
  • 2011-07-28
相关资源
最近更新 更多