2018年4月14日土曜日

OpenCVでビデオキャプチャが遅く感じるとき

事象

OpenCVでビデオキャプチャの画像を表示すると遅くなる場合がある。
例えば、このようなコードを書いたときに遅くなる(Python, C++に関係なく発生する)。
以下はPythonコード。

cap = cv2.VideoCapture(0)
while (True):
    ret, frame = cap.read()

    # 何か重い処理

    cv2.imshow("camera", frame)
    key = cv2.waitKey(1) & 0xff
    if key == 27:
        break

原因

これは、OpenCVはキャプチャした画像はバッファリングしているが、重い処理が原因で常にバッファの一番最後の画像を取得してしまうので遅くなってしまう(タイムラグが発生してしまう)。

解決方法

ビデオキャプチャのループ処理は設定したビデオキャプチャで指定したFPS内で処理できるようにすること。つまり、重い処理をしてはいけない。
どうしても重い処理を行うのであれば、

  • ビデオキャプチャのFPSを下げる(CV_CAP_PROP_FPSを指定)
  • ビデオキャプチャのループと何か重い処理を別スレッドにする(処理しないフレームが発生する)
のいずれかが必要。これは「何か重い処理」の内容を見極めて対応する必要がある。